├── .gitignore ├── 00_environment_setup.ipynb ├── 01_completion_api.ipynb ├── 02_OpenAI_parameters.ipynb ├── 03_chat_completion.ipynb ├── 04_embeddings.ipynb ├── 05_langchain_embeddings.ipynb ├── 06_functions_classificacao_sentimentos.ipynb ├── 07_functions_extraction.ipynb ├── 07_functions_reservation.ipynb ├── 08_functions_banco.ipynb ├── 09_multimodal.ipynb ├── 10_autogen_agents.ipynb ├── 11_autogen_group_chat.ipynb ├── bankdomain.py ├── data ├── cnn_dailymail_data.csv ├── constituicao.txt └── constituicao │ ├── index.faiss │ └── index.pkl └── jupyter.sh /.gitignore: -------------------------------------------------------------------------------- 1 | .env 2 | .ipynb_checkpoints 3 | .venv 4 | __pycache__ 5 | .cache -------------------------------------------------------------------------------- /00_environment_setup.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "d37c89c9-77cb-4f32-ab78-1fee414c78e9", 6 | "metadata": { 7 | "nteract": { 8 | "transient": { 9 | "deleting": false 10 | } 11 | }, 12 | "tags": [] 13 | }, 14 | "source": [ 15 | "# Setup do Ambiente\n", 16 | "\n", 17 | "Este notebook serve para instalar as bibliotecas e garantir que o seu ambiente está operacional\n" 18 | ] 19 | }, 20 | { 21 | "cell_type": "code", 22 | "execution_count": 1, 23 | "id": "b4b2bbe6-8b5b-45cf-b4ad-29e32099a0de", 24 | "metadata": { 25 | "tags": [] 26 | }, 27 | "outputs": [ 28 | { 29 | "name": "stdout", 30 | "output_type": "stream", 31 | "text": [ 32 | "Requirement already satisfied: openai in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (1.42.0)\n", 33 | "Requirement already satisfied: python-dotenv in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (1.0.1)\n", 34 | "Requirement already satisfied: langchain in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (0.2.15)\n", 35 | "Requirement already satisfied: plotly in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (5.23.0)\n", 36 | "Requirement already satisfied: scikit-learn in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (1.5.1)\n", 37 | "Requirement already satisfied: tiktoken in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (0.7.0)\n", 38 | "Requirement already satisfied: faiss-cpu in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (1.8.0.post1)\n", 39 | "Requirement already satisfied: langchain-openai in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (0.1.23)\n", 40 | "Requirement already satisfied: pandas in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (2.2.2)\n", 41 | "Requirement already satisfied: langchain_community in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (0.2.13)\n", 42 | "Collecting pyautogen\n", 43 | " Downloading pyautogen-0.2.35-py3-none-any.whl.metadata (27 kB)\n", 44 | "Requirement already satisfied: anyio<5,>=3.5.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from openai) (4.4.0)\n", 45 | "Requirement already satisfied: distro<2,>=1.7.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from openai) (1.9.0)\n", 46 | "Requirement already satisfied: httpx<1,>=0.23.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from openai) (0.27.2)\n", 47 | "Requirement already satisfied: jiter<1,>=0.4.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from openai) (0.5.0)\n", 48 | "Requirement already satisfied: pydantic<3,>=1.9.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from openai) (2.8.2)\n", 49 | "Requirement already satisfied: sniffio in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from openai) (1.3.1)\n", 50 | "Requirement already satisfied: tqdm>4 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from openai) (4.66.5)\n", 51 | "Requirement already satisfied: typing-extensions<5,>=4.11 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from openai) (4.12.2)\n", 52 | "Requirement already satisfied: PyYAML>=5.3 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (6.0.2)\n", 53 | "Requirement already satisfied: SQLAlchemy<3,>=1.4 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (2.0.32)\n", 54 | "Requirement already satisfied: aiohttp<4.0.0,>=3.8.3 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (3.10.5)\n", 55 | "Requirement already satisfied: langchain-core<0.3.0,>=0.2.35 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (0.2.35)\n", 56 | "Requirement already satisfied: langchain-text-splitters<0.3.0,>=0.2.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (0.2.2)\n", 57 | "Requirement already satisfied: langsmith<0.2.0,>=0.1.17 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (0.1.106)\n", 58 | "Requirement already satisfied: numpy<2.0.0,>=1.26.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (1.26.4)\n", 59 | "Requirement already satisfied: requests<3,>=2 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (2.32.3)\n", 60 | "Requirement already satisfied: tenacity!=8.4.0,<9.0.0,>=8.1.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain) (8.5.0)\n", 61 | "Requirement already satisfied: packaging in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from plotly) (24.1)\n", 62 | "Requirement already satisfied: scipy>=1.6.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from scikit-learn) (1.14.1)\n", 63 | "Requirement already satisfied: joblib>=1.2.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from scikit-learn) (1.4.2)\n", 64 | "Requirement already satisfied: threadpoolctl>=3.1.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from scikit-learn) (3.5.0)\n", 65 | "Requirement already satisfied: regex>=2022.1.18 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from tiktoken) (2024.7.24)\n", 66 | "Requirement already satisfied: python-dateutil>=2.8.2 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from pandas) (2.9.0.post0)\n", 67 | "Requirement already satisfied: pytz>=2020.1 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from pandas) (2024.1)\n", 68 | "Requirement already satisfied: tzdata>=2022.7 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from pandas) (2024.1)\n", 69 | "Requirement already satisfied: dataclasses-json<0.7,>=0.5.7 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain_community) (0.6.7)\n", 70 | "Collecting diskcache (from pyautogen)\n", 71 | " Downloading diskcache-5.6.3-py3-none-any.whl.metadata (20 kB)\n", 72 | "Collecting docker (from pyautogen)\n", 73 | " Downloading docker-7.1.0-py3-none-any.whl.metadata (3.8 kB)\n", 74 | "Collecting flaml (from pyautogen)\n", 75 | " Downloading FLAML-2.2.0-py3-none-any.whl.metadata (15 kB)\n", 76 | "Collecting termcolor (from pyautogen)\n", 77 | " Downloading termcolor-2.4.0-py3-none-any.whl.metadata (6.1 kB)\n", 78 | "Requirement already satisfied: aiohappyeyeballs>=2.3.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from aiohttp<4.0.0,>=3.8.3->langchain) (2.4.0)\n", 79 | "Requirement already satisfied: aiosignal>=1.1.2 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from aiohttp<4.0.0,>=3.8.3->langchain) (1.3.1)\n", 80 | "Requirement already satisfied: attrs>=17.3.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from aiohttp<4.0.0,>=3.8.3->langchain) (24.2.0)\n", 81 | "Requirement already satisfied: frozenlist>=1.1.1 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from aiohttp<4.0.0,>=3.8.3->langchain) (1.4.1)\n", 82 | "Requirement already satisfied: multidict<7.0,>=4.5 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from aiohttp<4.0.0,>=3.8.3->langchain) (6.0.5)\n", 83 | "Requirement already satisfied: yarl<2.0,>=1.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from aiohttp<4.0.0,>=3.8.3->langchain) (1.9.4)\n", 84 | "Requirement already satisfied: idna>=2.8 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from anyio<5,>=3.5.0->openai) (3.8)\n", 85 | "Requirement already satisfied: marshmallow<4.0.0,>=3.18.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from dataclasses-json<0.7,>=0.5.7->langchain_community) (3.22.0)\n", 86 | "Requirement already satisfied: typing-inspect<1,>=0.4.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from dataclasses-json<0.7,>=0.5.7->langchain_community) (0.9.0)\n", 87 | "Requirement already satisfied: certifi in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from httpx<1,>=0.23.0->openai) (2024.7.4)\n", 88 | "Requirement already satisfied: httpcore==1.* in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from httpx<1,>=0.23.0->openai) (1.0.5)\n", 89 | "Requirement already satisfied: h11<0.15,>=0.13 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from httpcore==1.*->httpx<1,>=0.23.0->openai) (0.14.0)\n", 90 | "Requirement already satisfied: jsonpatch<2.0,>=1.33 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langchain-core<0.3.0,>=0.2.35->langchain) (1.33)\n", 91 | "Requirement already satisfied: orjson<4.0.0,>=3.9.14 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from langsmith<0.2.0,>=0.1.17->langchain) (3.10.7)\n", 92 | "Requirement already satisfied: annotated-types>=0.4.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from pydantic<3,>=1.9.0->openai) (0.7.0)\n", 93 | "Requirement already satisfied: pydantic-core==2.20.1 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from pydantic<3,>=1.9.0->openai) (2.20.1)\n", 94 | "Requirement already satisfied: six>=1.5 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from python-dateutil>=2.8.2->pandas) (1.16.0)\n", 95 | "Requirement already satisfied: charset-normalizer<4,>=2 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from requests<3,>=2->langchain) (3.3.2)\n", 96 | "Requirement already satisfied: urllib3<3,>=1.21.1 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from requests<3,>=2->langchain) (2.2.2)\n", 97 | "Requirement already satisfied: greenlet!=0.4.17 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from SQLAlchemy<3,>=1.4->langchain) (3.0.3)\n", 98 | "Requirement already satisfied: colorama in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from tqdm>4->openai) (0.4.6)\n", 99 | "Requirement already satisfied: pywin32>=304 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from docker->pyautogen) (306)\n", 100 | "Requirement already satisfied: jsonpointer>=1.9 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from jsonpatch<2.0,>=1.33->langchain-core<0.3.0,>=0.2.35->langchain) (3.0.0)\n", 101 | "Requirement already satisfied: mypy-extensions>=0.3.0 in c:\\dev\\openai\\azureopenaitutorial\\.venv\\lib\\site-packages (from typing-inspect<1,>=0.4.0->dataclasses-json<0.7,>=0.5.7->langchain_community) (1.0.0)\n", 102 | "Downloading pyautogen-0.2.35-py3-none-any.whl (318 kB)\n", 103 | "Downloading diskcache-5.6.3-py3-none-any.whl (45 kB)\n", 104 | "Downloading docker-7.1.0-py3-none-any.whl (147 kB)\n", 105 | "Downloading FLAML-2.2.0-py3-none-any.whl (297 kB)\n", 106 | "Downloading termcolor-2.4.0-py3-none-any.whl (7.7 kB)\n", 107 | "Installing collected packages: termcolor, flaml, diskcache, docker, pyautogen\n", 108 | "Successfully installed diskcache-5.6.3 docker-7.1.0 flaml-2.2.0 pyautogen-0.2.35 termcolor-2.4.0\n", 109 | "Note: you may need to restart the kernel to use updated packages.\n" 110 | ] 111 | } 112 | ], 113 | "source": [ 114 | "pip install openai python-dotenv langchain plotly scikit-learn tiktoken faiss-cpu langchain-openai pandas langchain_community pyautogen" 115 | ] 116 | }, 117 | { 118 | "cell_type": "code", 119 | "execution_count": 8, 120 | "id": "d9ee5317-298f-4c9d-bb98-c52459d6f160", 121 | "metadata": { 122 | "tags": [] 123 | }, 124 | "outputs": [], 125 | "source": [ 126 | "import os\n", 127 | "from openai import AzureOpenAI\n", 128 | "from dotenv import load_dotenv\n", 129 | "load_dotenv()\n", 130 | "\n", 131 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 132 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 133 | "\n", 134 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 135 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 136 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 137 | "\n", 138 | "client = AzureOpenAI(\n", 139 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 140 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 141 | " api_key = API_KEY,\n", 142 | ")\n", 143 | "\n", 144 | "\n", 145 | "\n" 146 | ] 147 | }, 148 | { 149 | "cell_type": "code", 150 | "execution_count": 9, 151 | "id": "67e8d27d-397f-4860-bcd2-85bcea88344a", 152 | "metadata": { 153 | "tags": [] 154 | }, 155 | "outputs": [ 156 | { 157 | "name": "stdout", 158 | "output_type": "stream", 159 | "text": [ 160 | "ChatCompletion(id='chatcmpl-A1L6C7A406BhFUGCLLCXmtZ2QFlU0', choices=[Choice(finish_reason='stop', index=0, logprobs=None, message=ChatCompletionMessage(content=\"Hello! I'm an AI language model, so I don't have feelings, but I'm here and ready to help you. How can I assist you today?\", refusal=None, role='assistant', function_call=None, tool_calls=None), content_filter_results={'hate': {'filtered': False, 'severity': 'safe'}, 'self_harm': {'filtered': False, 'severity': 'safe'}, 'sexual': {'filtered': False, 'severity': 'safe'}, 'violence': {'filtered': False, 'severity': 'safe'}})], created=1724882796, model='gpt-4o-2024-05-13', object='chat.completion', service_tier=None, system_fingerprint='fp_abc28019ad', usage=CompletionUsage(completion_tokens=30, prompt_tokens=13, total_tokens=43), prompt_filter_results=[{'prompt_index': 0, 'content_filter_results': {'hate': {'filtered': False, 'severity': 'safe'}, 'jailbreak': {'filtered': False, 'detected': False}, 'self_harm': {'filtered': False, 'severity': 'safe'}, 'sexual': {'filtered': False, 'severity': 'safe'}, 'violence': {'filtered': False, 'severity': 'safe'}}}])\n", 161 | "Hello! I'm an AI language model, so I don't have feelings, but I'm here and ready to help you. How can I assist you today?\n" 162 | ] 163 | } 164 | ], 165 | "source": [ 166 | "# Simple API Call\n", 167 | "\n", 168 | "completion = client.chat.completions.create(\n", 169 | " model=\"gpt-4o\",\n", 170 | " messages=[\n", 171 | " {\n", 172 | " \"role\": \"user\",\n", 173 | " \"content\": \"Hello, how are you?\",\n", 174 | " },\n", 175 | " ],\n", 176 | ")\n", 177 | "\n", 178 | "print(completion)\n", 179 | "print(completion.choices[0].message.content)" 180 | ] 181 | }, 182 | { 183 | "cell_type": "code", 184 | "execution_count": null, 185 | "id": "26c324b0-5f21-4fe8-898c-a1bc55526750", 186 | "metadata": {}, 187 | "outputs": [], 188 | "source": [] 189 | } 190 | ], 191 | "metadata": { 192 | "kernelspec": { 193 | "display_name": "Python 3 (ipykernel)", 194 | "language": "python", 195 | "name": "python3" 196 | }, 197 | "language_info": { 198 | "codemirror_mode": { 199 | "name": "ipython", 200 | "version": 3 201 | }, 202 | "file_extension": ".py", 203 | "mimetype": "text/x-python", 204 | "name": "python", 205 | "nbconvert_exporter": "python", 206 | "pygments_lexer": "ipython3", 207 | "version": "3.12.4" 208 | } 209 | }, 210 | "nbformat": 4, 211 | "nbformat_minor": 5 212 | } 213 | -------------------------------------------------------------------------------- /01_completion_api.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": { 6 | "nteract": { 7 | "transient": { 8 | "deleting": false 9 | } 10 | }, 11 | "tags": [] 12 | }, 13 | "source": [ 14 | "# API de Completion\n", 15 | "\n", 16 | "Este notebook serve para mostrar o funcionamento das APIS de completion.\n", 17 | "Primeiro montamos o ambiente:\n" 18 | ] 19 | }, 20 | { 21 | "cell_type": "code", 22 | "execution_count": 1, 23 | "metadata": { 24 | "tags": [] 25 | }, 26 | "outputs": [ 27 | { 28 | "data": { 29 | "text/plain": [ 30 | "'gpt-35-turbo-instruct'" 31 | ] 32 | }, 33 | "execution_count": 1, 34 | "metadata": {}, 35 | "output_type": "execute_result" 36 | } 37 | ], 38 | "source": [ 39 | "import os\n", 40 | "from openai import AzureOpenAI\n", 41 | "from dotenv import load_dotenv\n", 42 | "load_dotenv()\n", 43 | "\n", 44 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 45 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 46 | "\n", 47 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 48 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 49 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 50 | "\n", 51 | "client = AzureOpenAI(\n", 52 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 53 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 54 | " api_key = API_KEY,\n", 55 | ")\n", 56 | "\n", 57 | "\n", 58 | "COMPLETIONS_MODEL = os.getenv('DEPLOYMENT_NAME')\n" 59 | ] 60 | }, 61 | { 62 | "cell_type": "markdown", 63 | "metadata": { 64 | "nteract": { 65 | "transient": { 66 | "deleting": false 67 | } 68 | }, 69 | "tags": [] 70 | }, 71 | "source": [ 72 | "## Chamada básica\n", 73 | "\n", 74 | "Para chamar, passamos o parametro Prompt, com o texto que queremos que ele complete.\n", 75 | "\n", 76 | "### Zero Shot Prompt\n" 77 | ] 78 | }, 79 | { 80 | "cell_type": "code", 81 | "execution_count": 18, 82 | "metadata": { 83 | "tags": [] 84 | }, 85 | "outputs": [ 86 | { 87 | "data": { 88 | "text/plain": [ 89 | "'How are you?'" 90 | ] 91 | }, 92 | "execution_count": 18, 93 | "metadata": {}, 94 | "output_type": "execute_result" 95 | } 96 | ], 97 | "source": [ 98 | "prompt = \"\"\"Traduza do Português para inglês:\n", 99 | "\n", 100 | "Como você vai? -> \"\"\"\n", 101 | "\n", 102 | "\n", 103 | "client.completions.create(\n", 104 | " prompt=prompt,\n", 105 | " temperature=0,\n", 106 | " max_tokens=1000,\n", 107 | " top_p=1,\n", 108 | " frequency_penalty=0,\n", 109 | " presence_penalty=0,\n", 110 | " model=COMPLETIONS_MODEL\n", 111 | ").choices[0].text.strip(\" \\n\")" 112 | ] 113 | }, 114 | { 115 | "cell_type": "markdown", 116 | "metadata": { 117 | "nteract": { 118 | "transient": { 119 | "deleting": false 120 | } 121 | }, 122 | "tags": [] 123 | }, 124 | "source": [ 125 | "### One Shot Prompt\n" 126 | ] 127 | }, 128 | { 129 | "cell_type": "code", 130 | "execution_count": 19, 131 | "metadata": { 132 | "tags": [] 133 | }, 134 | "outputs": [ 135 | { 136 | "data": { 137 | "text/plain": [ 138 | "'How are you doing?'" 139 | ] 140 | }, 141 | "execution_count": 19, 142 | "metadata": {}, 143 | "output_type": "execute_result" 144 | } 145 | ], 146 | "source": [ 147 | "prompt = \"\"\"Traduza do Português para inglês:\n", 148 | "\n", 149 | "Oi, tudo bem? -> Hi, how are you?\n", 150 | "Como você vai?-> \"\"\"\n", 151 | "client.completions.create(\n", 152 | " prompt=prompt,\n", 153 | " temperature=0,\n", 154 | " max_tokens=1000,\n", 155 | " top_p=1,\n", 156 | " frequency_penalty=0,\n", 157 | " presence_penalty=0,\n", 158 | " model=COMPLETIONS_MODEL\n", 159 | ").choices[0].text.strip(\" \\n\")" 160 | ] 161 | }, 162 | { 163 | "cell_type": "markdown", 164 | "metadata": { 165 | "nteract": { 166 | "transient": { 167 | "deleting": false 168 | } 169 | }, 170 | "tags": [] 171 | }, 172 | "source": [ 173 | "### Few Shot Prompt\n" 174 | ] 175 | }, 176 | { 177 | "cell_type": "code", 178 | "execution_count": 23, 179 | "metadata": { 180 | "tags": [] 181 | }, 182 | "outputs": [ 183 | { 184 | "data": { 185 | "text/plain": [ 186 | "'How are you doing?'" 187 | ] 188 | }, 189 | "execution_count": 23, 190 | "metadata": {}, 191 | "output_type": "execute_result" 192 | } 193 | ], 194 | "source": [ 195 | "prompt = \"\"\"Traduza do Português para inglês:\n", 196 | "\n", 197 | "Oi, tudo bem? -> Hi, how are you?\n", 198 | "Me chamo André -> My name is André\n", 199 | "Como você vai? -> \"\"\"\n", 200 | "client.completions.create(\n", 201 | " prompt=prompt,\n", 202 | " temperature=0,\n", 203 | " max_tokens=1000,\n", 204 | " top_p=1,\n", 205 | " frequency_penalty=0,\n", 206 | " presence_penalty=0,\n", 207 | " model=COMPLETIONS_MODEL,\n", 208 | " stop=[\"\\n\"]\n", 209 | ").choices[0].text.strip(\" \\n\")" 210 | ] 211 | }, 212 | { 213 | "cell_type": "markdown", 214 | "metadata": { 215 | "nteract": { 216 | "transient": { 217 | "deleting": false 218 | } 219 | }, 220 | "tags": [] 221 | }, 222 | "source": [ 223 | "### Tradução\n" 224 | ] 225 | }, 226 | { 227 | "cell_type": "code", 228 | "execution_count": 24, 229 | "metadata": { 230 | "tags": [] 231 | }, 232 | "outputs": [ 233 | { 234 | "name": "stdout", 235 | "output_type": "stream", 236 | "text": [ 237 | "1. Please, I would like a water.\n", 238 | "2. Por favor, me gustaría un agua.\n", 239 | "3. お願いします、水をお願いします。\n", 240 | "4. من فضلك، أود ماء واحد.\n" 241 | ] 242 | } 243 | ], 244 | "source": [ 245 | "prompt = \"\"\"Traduza a seguinte frase para 1. Inglês, 2. Espanhol, 3. Japonês, 4. Arábe: Por favor, gostaria de uma Água\n", 246 | "\"\"\"\n", 247 | "print(client.completions.create(\n", 248 | " prompt=prompt,\n", 249 | " temperature=0,\n", 250 | " max_tokens=1000,\n", 251 | " top_p=1,\n", 252 | " frequency_penalty=0,\n", 253 | " presence_penalty=0,\n", 254 | " model=COMPLETIONS_MODEL\n", 255 | ").choices[0].text.strip(\" \\n\"))" 256 | ] 257 | }, 258 | { 259 | "cell_type": "markdown", 260 | "metadata": { 261 | "nteract": { 262 | "transient": { 263 | "deleting": false 264 | } 265 | }, 266 | "tags": [] 267 | }, 268 | "source": [ 269 | "### Geração de Ideias\n" 270 | ] 271 | }, 272 | { 273 | "cell_type": "code", 274 | "execution_count": 25, 275 | "metadata": { 276 | "tags": [] 277 | }, 278 | "outputs": [ 279 | { 280 | "name": "stdout", 281 | "output_type": "stream", 282 | "text": [ 283 | "1. \"As principais tendências em arquitetura de sistemas para profissionais senior\" - Neste post, podemos abordar as tendências atuais e emergentes na área de arquitetura de sistemas, como computação em nuvem, microsserviços, internet das coisas e inteligência artificial. Será possível discutir os benefícios e desafios de cada tendência, além de como os profissionais senior podem se atualizar e se adaptar a essas mudanças no mercado.\n", 284 | "\n", 285 | "2. \"Como a arquitetura de sistemas pode impulsionar a transformação digital nas empresas\" - A transformação digital é uma realidade cada vez mais presente nas empresas e a arquitetura de sistemas desempenha um papel fundamental nesse processo. Neste post, podemos explorar como os profissionais senior de arquitetura podem ajudar as empresas a alcançar seus objetivos de transformação digital, através do desenvolvimento de sistemas eficientes, escaláveis e seguros.\n", 286 | "\n", 287 | "3. \"A importância da gestão de mudanças na arquitetura de sistemas para profissionais senior\" - A arquitetura de sistemas não é apenas sobre a criação de soluções tecnológicas, mas também envolve a gestão de mudanças e o controle de riscos. Neste post, podemos abordar como os profissionais senior de arquitetura podem atuar na gestão de mudanças de forma efetiva, minimizando possíveis impactos e garantindo a continuidade dos sistemas de forma sustentável. Será possível também discutir técnicas e ferramentas utilizadas nessa gestão, assim como boas práticas recomendadas.\n" 288 | ] 289 | } 290 | ], 291 | "source": [ 292 | "prompt = \"\"\"Gere 3 idéias de posts de blog sobre Arquitetura de sistemas para profissionais senior:\n", 293 | "\n", 294 | "\"\"\"\n", 295 | "print(client.completions.create(\n", 296 | " prompt=prompt,\n", 297 | " temperature=0.9,\n", 298 | " max_tokens=1000,\n", 299 | " top_p=1,\n", 300 | " frequency_penalty=0,\n", 301 | " presence_penalty=0,\n", 302 | " model=COMPLETIONS_MODEL\n", 303 | ").choices[0].text.strip(\" \\n\"))" 304 | ] 305 | }, 306 | { 307 | "cell_type": "markdown", 308 | "metadata": { 309 | "nteract": { 310 | "transient": { 311 | "deleting": false 312 | } 313 | }, 314 | "tags": [] 315 | }, 316 | "source": [ 317 | "### Classificação\n" 318 | ] 319 | }, 320 | { 321 | "cell_type": "code", 322 | "execution_count": 26, 323 | "metadata": { 324 | "tags": [] 325 | }, 326 | "outputs": [ 327 | { 328 | "name": "stdout", 329 | "output_type": "stream", 330 | "text": [ 331 | "Positivo\n" 332 | ] 333 | } 334 | ], 335 | "source": [ 336 | "prompt = \"\"\"Decida se o Tweet abaixo é positivo, negativo ou neutro.\n", 337 | "\n", 338 | "Tweet: Estou animado para estréia do Rings of Power amanhã!\n", 339 | "Sentimento:\"\"\"\n", 340 | "print(client.completions.create(\n", 341 | " prompt=prompt,\n", 342 | " temperature=0,\n", 343 | " max_tokens=1000,\n", 344 | " top_p=1,\n", 345 | " frequency_penalty=0,\n", 346 | " presence_penalty=0,\n", 347 | " model=COMPLETIONS_MODEL\n", 348 | ").choices[0].text.strip(\" \\n\"))" 349 | ] 350 | }, 351 | { 352 | "cell_type": "code", 353 | "execution_count": 27, 354 | "metadata": { 355 | "tags": [] 356 | }, 357 | "outputs": [ 358 | { 359 | "name": "stdout", 360 | "output_type": "stream", 361 | "text": [ 362 | "Negativo\n" 363 | ] 364 | } 365 | ], 366 | "source": [ 367 | "prompt = \"\"\"Decida se o Tweet abaixo é positivo, negativo ou neutro. \n", 368 | "\n", 369 | "Tweet: Estou animado para estréia do Rings of Power amanhã! SQN!\n", 370 | "Sentimento:\"\"\"\n", 371 | "print(client.completions.create(\n", 372 | " prompt=prompt,\n", 373 | " temperature=0,\n", 374 | " max_tokens=1000,\n", 375 | " top_p=1,\n", 376 | " frequency_penalty=0,\n", 377 | " presence_penalty=0,\n", 378 | " model=COMPLETIONS_MODEL\n", 379 | ").choices[0].text.strip(\" \\n\"))" 380 | ] 381 | }, 382 | { 383 | "cell_type": "code", 384 | "execution_count": 30, 385 | "metadata": { 386 | "tags": [] 387 | }, 388 | "outputs": [ 389 | { 390 | "name": "stdout", 391 | "output_type": "stream", 392 | "text": [ 393 | "Positivo\n", 394 | "Sarcasmo: Sim\n" 395 | ] 396 | } 397 | ], 398 | "source": [ 399 | "prompt = \"\"\"Decida se o Tweet abaixo é positivo, negativo ou neutro. Avalie se tem sarcasmo.\n", 400 | "\n", 401 | "Tweet: O Hotel é bom que dói.\n", 402 | "Sentimento: Negativo\n", 403 | "Sarcasmo: Sim\n", 404 | "\n", 405 | "Tweet: O Hotel é tão chique que até as baratas usam gravatas.\n", 406 | "Sentimento:\"\"\"\n", 407 | "print(client.completions.create(\n", 408 | " prompt=prompt,\n", 409 | " temperature=0,\n", 410 | " max_tokens=1000,\n", 411 | " top_p=1,\n", 412 | " frequency_penalty=0,\n", 413 | " presence_penalty=0,\n", 414 | " model=COMPLETIONS_MODEL\n", 415 | ").choices[0].text.strip(\" \\n\"))" 416 | ] 417 | }, 418 | { 419 | "cell_type": "code", 420 | "execution_count": 31, 421 | "metadata": { 422 | "tags": [] 423 | }, 424 | "outputs": [ 425 | { 426 | "name": "stdout", 427 | "output_type": "stream", 428 | "text": [ 429 | "Positivo\n", 430 | "Sarcasmo: Não\n" 431 | ] 432 | } 433 | ], 434 | "source": [ 435 | "prompt = \"\"\"Decida se o Tweet abaixo é positivo, negativo ou neutro. Avalie se tem sarcasmo.\n", 436 | "\n", 437 | "Tweet: O Hotel é bom que dói.\n", 438 | "Sentimento: Negativo\n", 439 | "Sarcasmo: Sim\n", 440 | "\n", 441 | "Tweet: O Hotel é muito chique.\n", 442 | "Sentimento:\"\"\"\n", 443 | "print(client.completions.create(\n", 444 | " prompt=prompt,\n", 445 | " temperature=0,\n", 446 | " max_tokens=1000,\n", 447 | " top_p=1,\n", 448 | " frequency_penalty=0,\n", 449 | " presence_penalty=0,\n", 450 | " model=COMPLETIONS_MODEL\n", 451 | ").choices[0].text.strip(\" \\n\"))" 452 | ] 453 | } 454 | ], 455 | "metadata": { 456 | "kernelspec": { 457 | "display_name": "Python 3 (ipykernel)", 458 | "language": "python", 459 | "name": "python3" 460 | }, 461 | "language_info": { 462 | "codemirror_mode": { 463 | "name": "ipython", 464 | "version": 3 465 | }, 466 | "file_extension": ".py", 467 | "mimetype": "text/x-python", 468 | "name": "python", 469 | "nbconvert_exporter": "python", 470 | "pygments_lexer": "ipython3", 471 | "version": "3.12.4" 472 | }, 473 | "vscode": { 474 | "interpreter": { 475 | "hash": "0ac0e7d245f35f05656c1dae54880a0902b050693b3e66826fb0a7033a44f77d" 476 | } 477 | } 478 | }, 479 | "nbformat": 4, 480 | "nbformat_minor": 4 481 | } 482 | -------------------------------------------------------------------------------- /02_OpenAI_parameters.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "# Parametros da OpenAI" 8 | ] 9 | }, 10 | { 11 | "cell_type": "code", 12 | "execution_count": 1, 13 | "metadata": { 14 | "tags": [] 15 | }, 16 | "outputs": [], 17 | "source": [ 18 | "import os\n", 19 | "from openai import AzureOpenAI\n", 20 | "from dotenv import load_dotenv\n", 21 | "load_dotenv()\n", 22 | "\n", 23 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 24 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 25 | "\n", 26 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 27 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 28 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 29 | "\n", 30 | "client = AzureOpenAI(\n", 31 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 32 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 33 | " api_key = API_KEY,\n", 34 | ")" 35 | ] 36 | }, 37 | { 38 | "cell_type": "markdown", 39 | "metadata": {}, 40 | "source": [ 41 | "# temperature\n", 42 | "\n", 43 | "Padrão é 1.\n", 44 | "\n", 45 | "Pode ser visto como a \"Criatividade\" do modelo. Um valor mais algo, significa que o modelo vai tomar mais risco. Usamos 0.9 para aplicações mais criativas e 0 para as que queremos uma resposta bem definida.\n", 46 | "\n", 47 | "Não é recomendado alterar temperature e top_p ao mesmo tempo." 48 | ] 49 | }, 50 | { 51 | "cell_type": "code", 52 | "execution_count": 12, 53 | "metadata": { 54 | "tags": [] 55 | }, 56 | "outputs": [], 57 | "source": [ 58 | "def call_openai(num_times, prompt, temperature):\n", 59 | " for i in range(num_times):\n", 60 | " \n", 61 | " response = client.completions.create(\n", 62 | " model=os.getenv('DEPLOYMENT_NAME'),\n", 63 | " prompt=prompt,\n", 64 | " max_tokens=60,\n", 65 | " temperature = temperature\n", 66 | " )\n", 67 | " print(response.choices[0].text)" 68 | ] 69 | }, 70 | { 71 | "cell_type": "code", 72 | "execution_count": 13, 73 | "metadata": { 74 | "tags": [] 75 | }, 76 | "outputs": [ 77 | { 78 | "name": "stdout", 79 | "output_type": "stream", 80 | "text": [ 81 | "cão. Eles são leais, amorosos, companheiros e sempre estão prontos para nos fazer companhia e nos alegrar. Além disso, os cães são ótimos para praticar exercícios e nos ajudam a manter uma\n", 82 | "cão. Eles são leais, amorosos, companheiros e sempre estão prontos para nos fazer companhia e nos alegrar. Além disso, os cães são ótimos para praticar exercícios e nos ajudam a manter uma\n", 83 | "cão. Eles são leais, amorosos, companheiros e sempre estão prontos para nos fazer companhia e nos alegrar. Além disso, os cães são ótimos para praticar exercícios e nos ajudam a manter uma\n" 84 | ] 85 | } 86 | ], 87 | "source": [ 88 | "call_openai(3, 'O melhor animal de estimação é o ', temperature = 0)" 89 | ] 90 | }, 91 | { 92 | "cell_type": "code", 93 | "execution_count": 14, 94 | "metadata": { 95 | "tags": [] 96 | }, 97 | "outputs": [ 98 | { 99 | "name": "stdout", 100 | "output_type": "stream", 101 | "text": [ 102 | "cão.\n", 103 | "\n", 104 | "Os cães são conhecidos por serem leais, carinhosos e fiéis companheiros. Eles são capazes de criar laços fortes com seus donos e estão sempre prontos para dar amor e proteção. Além disso, os\n", 105 | "cão, pois ele é um excelente companheiro, fiel e leal ao seu dono. Além disso, os cães são inteligentes e podem ser treinados para realizar diversas atividades, como proteção, auxílio a pessoas com necessidades especiais e\n", 106 | "que melhor se adapta às suas necessidades, estilo de vida e capacidade de cuidar dele de forma responsável. Algumas pessoas preferem animais de estimação mais independentes, como gatos, enquanto outras gostam de animais mais interativos, como cachorros.\n", 107 | "cão. Eles são leais, amorosos e companheiros fiéis. Além disso, os cães têm a capacidade de se adaptar facilmente à rotina de suas famílias, seja vivendo em casa ou em espaços menores. Eles\n", 108 | "cão.\n", 109 | "\n", 110 | "Os cães são conhecidos por serem leais, carinhosos e protetores de seus donos. Eles também são ótimos companheiros e estão sempre prontos para brincar e fazer atividades com seus donos.\n", 111 | "\n", 112 | "Além dis\n", 113 | "que se encaixa perfeitamente ao estilo de vida e às necessidades do dono.\n", 114 | "\n", 115 | "Cada pessoa tem preferências e rotinas diferentes, o que pode influenciar na escolha do animal de estimação ideal. Algumas das características a serem consideradas ao escolher\n", 116 | "cão.\n", 117 | "\n", 118 | "Isso porque os cães possuem uma série de características que os tornam excelentes companheiros para nós humanos. Além disso, eles possuem habilidades únicas que os tornam úteis em diversas situações, tais como:\n", 119 | "\n", 120 | "1\n", 121 | "cachorro, pois eles são fiéis, amorosos, companheiros e sempre estarão ao nosso lado, nos dando carinho e proteção. Além disso, os cães também são ótimos para ajudar na segurança da casa, podem ser treinados\n", 122 | "cachorro. Existem várias razões pelas quais o cachorro é um excelente companheiro e animal de estimação. \n", 123 | "\n", 124 | "1. Amor e lealdade: Os cães são conhecidos por seu amor incondicional e lealdade aos seus donos\n", 125 | "que se encaixa melhor no estilo de vida e nas preferências de cada pessoa. Algumas pessoas podem preferir cães pela sua companhia e lealdade, outras podem preferir gatos pela sua independência e tranquilidade. Além disso, outros animais como\n" 126 | ] 127 | } 128 | ], 129 | "source": [ 130 | "call_openai(10, 'O melhor animal de estimação é o ', temperature = 1)" 131 | ] 132 | }, 133 | { 134 | "cell_type": "markdown", 135 | "metadata": {}, 136 | "source": [ 137 | "# top_p\n", 138 | "\n", 139 | "Padrão é 1\n", 140 | "\n", 141 | "Uma alternativa à temperatura. O Modelo irá considerar apenas os tokens com probabilidade igual a esse parametro. Então 0.1 significa que apenas as respostas com até 10% de probabilidae serão consideradas.\n", 142 | "\n", 143 | "Não é recomendado alterar temperature e top_p ao mesmo tempo." 144 | ] 145 | }, 146 | { 147 | "cell_type": "code", 148 | "execution_count": 15, 149 | "metadata": { 150 | "tags": [] 151 | }, 152 | "outputs": [], 153 | "source": [ 154 | "def call_openai_top_p(num_times, prompt, top_p):\n", 155 | " for i in range(num_times):\n", 156 | " \n", 157 | " response = client.completions.create(\n", 158 | " model=os.getenv('DEPLOYMENT_NAME'),\n", 159 | " prompt=prompt,\n", 160 | " max_tokens=70,\n", 161 | " top_p = top_p\n", 162 | " )\n", 163 | " print(response.choices[0].text)" 164 | ] 165 | }, 166 | { 167 | "cell_type": "code", 168 | "execution_count": 16, 169 | "metadata": { 170 | "tags": [] 171 | }, 172 | "outputs": [ 173 | { 174 | "name": "stdout", 175 | "output_type": "stream", 176 | "text": [ 177 | "cão, pois além de ser um companheiro fiel e carinhoso, também oferece muitos benefícios para a saúde física e mental de seus donos. Além disso, os cães são excelentes para exercícios físicos, são inteligentes e podem ser facilmente treinados para diversos fins\n", 178 | "cão. O cão é um animal extremamente leal e amoroso, que estará sempre ao lado do seu dono, independente das circunstâncias. Além disso, é um ótimo companheiro para atividades físicas, como caminhadas e corridas, o que pode ser benéf\n", 179 | "cão\n", 180 | "\n", 181 | "O cão é considerado o melhor animal de estimação por diversos motivos. Primeiramente, eles são extremamente leais e fiéis aos seus donos, formando laços afetivos muito fortes. Além disso, são excelentes companheiros, sempre prontos para brincar\n" 182 | ] 183 | } 184 | ], 185 | "source": [ 186 | "call_openai_top_p(3, 'O melhor animal de estimação é o ', top_p = 1)" 187 | ] 188 | }, 189 | { 190 | "cell_type": "code", 191 | "execution_count": 17, 192 | "metadata": { 193 | "tags": [] 194 | }, 195 | "outputs": [ 196 | { 197 | "name": "stdout", 198 | "output_type": "stream", 199 | "text": [ 200 | "cão. Eles são leais, amorosos, companheiros e sempre estão prontos para nos fazer companhia e nos alegrar. Além disso, os cães são ótimos para praticar exercícios e nos ajudam a manter uma rotina saudável. Eles também são\n", 201 | "cão. Eles são leais, amorosos, companheiros e sempre estão prontos para nos fazer companhia e nos alegrar. Além disso, os cães são ótimos para praticar exercícios e nos ajudam a manter uma rotina saudável. Eles também são\n", 202 | "cão. Eles são leais, amorosos, companheiros e sempre estão prontos para nos fazer companhia e nos alegrar. Além disso, os cães são ótimos para praticar exercícios e nos ajudam a manter uma rotina saudável. Eles também são\n" 203 | ] 204 | } 205 | ], 206 | "source": [ 207 | "call_openai_top_p(3, 'O melhor animal de estimação é o ', top_p = 0.1)" 208 | ] 209 | }, 210 | { 211 | "cell_type": "markdown", 212 | "metadata": {}, 213 | "source": [ 214 | "# n\n", 215 | "\n", 216 | "Padrão é 1\n", 217 | "\n", 218 | "Quantas alternativas serão geradas para cada prompt.\n", 219 | "\n", 220 | "Nota: Cada alternativa irá consumir tokens separadamente." 221 | ] 222 | }, 223 | { 224 | "cell_type": "code", 225 | "execution_count": 18, 226 | "metadata": { 227 | "tags": [] 228 | }, 229 | "outputs": [ 230 | { 231 | "name": "stdout", 232 | "output_type": "stream", 233 | "text": [ 234 | "cão. Isso pode variar de acordo com as preferências pessoais de cada indivíduo, mas há diversas razões que fazem do cão um ótimo animal de estimação:\n", 235 | "\n", 236 | "1. Fidelidade e companheirismo: os cães são\n", 237 | "cão.\n", 238 | "\n", 239 | "Os cães são conhecidos como os melhores animais de estimação por várias razões:\n", 240 | "\n", 241 | "1. Lealdade: Os cães são extremamente leais aos seus donos. Eles criam laços fortes e duradouros com\n" 242 | ] 243 | } 244 | ], 245 | "source": [ 246 | "response = client.completions.create(\n", 247 | " model=os.getenv('DEPLOYMENT_NAME'),\n", 248 | " prompt='O melhor animal de estimação é o ',\n", 249 | " max_tokens=60,\n", 250 | " n=2\n", 251 | " )\n", 252 | "\n", 253 | "for c in response.choices:\n", 254 | " print(c.text)" 255 | ] 256 | }, 257 | { 258 | "cell_type": "markdown", 259 | "metadata": {}, 260 | "source": [ 261 | "# logprobs\n", 262 | "\n", 263 | "Padrão é null (não retornar)\n", 264 | "\n", 265 | "Retorna a probabilidade dos tokens. Por exemplo, se logprobs for 5, a API irár retornar a lista dos 5 tokens mais provaveis. \n", 266 | "\n", 267 | "O maior valor permitido para logprobs é 5" 268 | ] 269 | }, 270 | { 271 | "cell_type": "code", 272 | "execution_count": 19, 273 | "metadata": { 274 | "tags": [] 275 | }, 276 | "outputs": [ 277 | { 278 | "name": "stdout", 279 | "output_type": "stream", 280 | "text": [ 281 | "Logprobs(text_offset=[33, 34, 37, 41, 42, 44, 47, 51, 58, 60, 64, 67, 70, 71, 75, 78, 82, 83, 86, 89, 91, 98, 104, 107, 113, 118, 125, 132, 136, 137, 140, 142, 146, 148, 149, 152, 157, 159, 162, 169, 173, 175, 178, 180, 185, 191, 197, 199, 202, 204, 215, 217, 222, 223, 225, 228, 231, 233, 240, 242], token_logprobs=[-0.37068087, -2.2398226, -0.0007965237, -0.5204445, -0.65042126, -0.0018291725, -0.0061275144, -1.046762, -0.00012356207, -0.00055398635, -0.69070584, -0.00066954794, -0.18299137, -1.4567846, -3.7623562e-05, -0.0011242642, -0.91026133, -0.7796487, -0.000685391, -0.059264258, -0.9698842, -0.57317513, -2.6178446, -0.052738994, -2.4272753e-05, -4.794611, -0.044157088, -0.00021521868, -0.28012067, -0.045092937, -0.0003361774, -0.0015728296, -0.00035012423, -2.6418418e-05, -1.6409781, -0.25089437, -0.00011188744, -0.00040874677, -1.589285, -0.61052316, -0.29629022, -0.00036037207, -0.011165371, -0.073080085, -1.6651225, -0.35204545, -0.038400967, -0.00026848805, -0.8902388, -5.2898097, -0.27823377, -0.7508502, -0.24130169, -0.57642287, -0.00079247804, -0.00051717076, -0.014497827, -0.0036538835, -0.00030733744, -0.46892318], tokens=['c', 'ach', 'orro', '.', ' E', 'les', ' são', ' compan', 'he', 'iros', ' fi', 'éis', ',', ' car', 'inh', 'osos', ',', ' le', 'ais', ' e', ' sempre', ' estão', ' ao', ' nosso', ' lado', ' quando', ' precis', 'amos', '.', ' Al', 'ém', ' dis', 'so', ',', ' os', ' cach', 'or', 'ros', ' também', ' são', ' ó', 'tim', 'os', ' para', ' fazer', ' exerc', 'íc', 'ios', ' e', ' proporcion', 'am', ' muit', 'a', ' a', 'leg', 'ria', ' e', ' divers', 'ão', ' para'], top_logprobs=[{'c': -0.37068087, 'que': -1.5234213}, {'ach': -2.2398226, 'ão': -0.11525744}, {'orro': -0.0007965237, 'orr': -7.958745}, {'.': -0.5204445, ',': -1.1988274}, {' E': -0.65042126, ' Al': -2.0913029}, {'les': -0.0018291725, '<|endoftext|>': -6.7320538}, {' são': -0.0061275144, ' ofere': -6.494933}, {' compan': -1.046762, ' le': -0.91539335}, {'he': -0.00012356207, 'h': -9.61219}, {'iros': -0.00055398635, 'ir': -8.043096}, {' fi': -0.69070584, ' le': -0.71915585}, {'éis': -0.00066954794, 'é': -7.4498405}, {',': -0.18299137, ' e': -1.7985462}, {' amor': -1.0364965, ' le': -1.2736963}, {'inh': -3.7623562e-05, 'i': -11.275004}, {'osos': -0.0011242642, 'os': -7.1778936}, {',': -0.91026133, ' e': -0.5149023}, {' le': -0.7796487, ' prot': -1.5358686}, {'ais': -0.000685391, 'ias': -8.078412}, {' e': -0.059264258, ',': -2.8556395}, {' sempre': -0.9698842, ' divert': -1.8993218}, {' estão': -0.57317513, ' pr': -1.1982038}, {' pr': -0.35935506, ' dis': -1.7702876}, {' nosso': -0.052738994, ' lado': -3.0610435}, {' lado': -2.4272753e-05, ' ': -11.50126}, {',': -0.38691527, ' nos': -1.9437199}, {' precis': -0.044157088, ' mais': -3.1489658}, {'amos': -0.00021521868, 'am': -9.561825}, {'.': -0.28012067, ' de': -1.4170263}, {' Al': -0.045092937, ' E': -4.0433173}, {'ém': -0.0003361774, 'é': -8.62127}, {' dis': -0.0015728296, ' de': -6.4769735}, {'so': -0.00035012423, 's': -8.157981}, {',': -2.6418418e-05, '<|endoftext|>': -10.827799}, {' os': -1.6409781, ' são': -0.481621}, {' cach': -0.25089437, ' c': -1.5065515}, {'or': -0.00011188744, 'o': -9.575637}, {'ros': -0.00040874677, 'r': -8.5766}, {' também': -1.589285, ' são': -0.6017934}, {' são': -0.61052316, ' podem': -1.6754799}, {' ó': -0.29629022, ' excel': -1.7373054}, {'tim': -0.00036037207, 't': -7.9906425}, {'os': -0.011165371, 'as': -4.513799}, {' para': -0.073080085, ' prot': -3.1094685}, {' pratic': -0.9487757, ' nos': -1.3287578}, {' exerc': -0.35204545, ' ativ': -1.3460678}, {'íc': -0.038400967, 'ício': -3.2801745}, {'ios': -0.00026848805, 'io': -8.953222}, {' e': -0.8902388, ',': -0.9772902}, {' nos': -0.9924502, ' br': -1.3497443}, {'am': -0.27823377, 'ar': -1.4223702}, {' muit': -0.7508502, ' momentos': -1.3004813}, {'a': -0.24130169, 'os': -1.8745147}, {' a': -0.57642287, ' divers': -0.83000106}, {'leg': -0.00079247804, 'le': -7.264592}, {'ria': -0.00051717076, 'ri': -8.056204}, {' e': -0.014497827, ' para': -5.3186474}, {' divers': -0.0036538835, ' fel': -7.2349944}, {'ão': -0.00030733744, 'ã': -8.203463}, {' para': -0.46892318, ' em': -1.4441773}])\n", 282 | "cachorro. Eles são companheiros fiéis, carinhosos, leais e sempre estão ao nosso lado quando precisamos. Além disso, os cachorros também são ótimos para fazer exercícios e proporcionam muita alegria e diversão para\n" 283 | ] 284 | } 285 | ], 286 | "source": [ 287 | "response = client.completions.create(\n", 288 | " model=os.getenv('DEPLOYMENT_NAME'),\n", 289 | " prompt='O melhor animal de estimação é o ',\n", 290 | " max_tokens=60,\n", 291 | " logprobs = 2,\n", 292 | " )\n", 293 | "\n", 294 | "print(response.choices[0].logprobs)\n", 295 | "print(response.choices[0].text)" 296 | ] 297 | } 298 | ], 299 | "metadata": { 300 | "kernelspec": { 301 | "display_name": "Python 3 (ipykernel)", 302 | "language": "python", 303 | "name": "python3" 304 | }, 305 | "language_info": { 306 | "codemirror_mode": { 307 | "name": "ipython", 308 | "version": 3 309 | }, 310 | "file_extension": ".py", 311 | "mimetype": "text/x-python", 312 | "name": "python", 313 | "nbconvert_exporter": "python", 314 | "pygments_lexer": "ipython3", 315 | "version": "3.12.4" 316 | }, 317 | "vscode": { 318 | "interpreter": { 319 | "hash": "2139c70ac98f3202d028164a545621647e07f47fd6f5d8ac55cf952bf7c15ed1" 320 | } 321 | } 322 | }, 323 | "nbformat": 4, 324 | "nbformat_minor": 4 325 | } 326 | -------------------------------------------------------------------------------- /03_chat_completion.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "e992deab-e6d6-4478-b58c-464d0dafc71d", 6 | "metadata": {}, 7 | "source": [ 8 | "# Chat Completion\n", 9 | "\n", 10 | "API para usar os modelos de chat da OpenAI (gpt-35-turbo, gpt-4, gpt-4-32k)\n" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": 1, 16 | "id": "b4f5e0eb-d71b-4821-a160-6da1e810377e", 17 | "metadata": { 18 | "tags": [] 19 | }, 20 | "outputs": [], 21 | "source": [ 22 | "import os\n", 23 | "from openai import AzureOpenAI\n", 24 | "from dotenv import load_dotenv\n", 25 | "load_dotenv()\n", 26 | "\n", 27 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 28 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 29 | "\n", 30 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 31 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 32 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 33 | "\n", 34 | "client = AzureOpenAI(\n", 35 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 36 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 37 | " api_key = API_KEY,\n", 38 | ")\n" 39 | ] 40 | }, 41 | { 42 | "cell_type": "code", 43 | "execution_count": 3, 44 | "id": "87ffc308-5fe5-41b5-8a95-3c5b7bdec610", 45 | "metadata": { 46 | "tags": [] 47 | }, 48 | "outputs": [], 49 | "source": [ 50 | "def build_message(role, content):\n", 51 | " return {\"role\":role, \"content\":content}" 52 | ] 53 | }, 54 | { 55 | "cell_type": "code", 56 | "execution_count": 5, 57 | "id": "2634b014-c3f1-4d25-a26a-7d62ee2c19b3", 58 | "metadata": { 59 | "tags": [] 60 | }, 61 | "outputs": [ 62 | { 63 | "name": "stdout", 64 | "output_type": "stream", 65 | "text": [ 66 | "Hmmm, dificuldades nos testes unitários, você tem. Escutar, você deve. Seguir esses passos, você vai:\n", 67 | "\n", 68 | "1. **Claridade no entendimento, buscar:**\n", 69 | " Compreender a funcionalidade que testar, você precisa. Documentação revisar, essencial é.\n", 70 | "\n", 71 | "2. **Ambiente de testes configurar, você deve:**\n", 72 | " Certificar-se de que o ambiente de desenvolvimento correto, você tem. Ferramentas de testes instaladas e corretamente configuradas, assegurar você deve.\n", 73 | "\n", 74 | "3. **Cobertura de testes aumentar, tentar:**\n", 75 | " Casos de testes abrangentes criar, você deve. Situações de sucesso e falha cobrir, você deve.\n", 76 | "\n", 77 | "4. **Dependências isolar, lembre-se:**\n", 78 | " Mocks e stubs usar para dependências, você deve. Independentes seus testes, manter, necessário é.\n", 79 | "\n", 80 | "5. **Erro nos testes analisar, você deve:**\n", 81 | " Logs e mensagens de erro, revisar com atenção, você deve. A raiz do problema, descobrir, tentar.\n", 82 | "\n", 83 | "6. **Aprendizado contínuo, buscar sempre:**\n", 84 | " Práticas de testes unitários, estudar continuamente, você deve. Comunidade de desenvolvedores e documentação, recorrer, útil é.\n", 85 | "\n", 86 | "Persistência e paciência, essenciais são. Melhorar suas habilidades de teste, com o tempo, você vai.\n" 87 | ] 88 | }, 89 | { 90 | "data": { 91 | "text/plain": [ 92 | "ChatCompletionMessage(content='Hmmm, dificuldades nos testes unitários, você tem. Escutar, você deve. Seguir esses passos, você vai:\\n\\n1. **Claridade no entendimento, buscar:**\\n Compreender a funcionalidade que testar, você precisa. Documentação revisar, essencial é.\\n\\n2. **Ambiente de testes configurar, você deve:**\\n Certificar-se de que o ambiente de desenvolvimento correto, você tem. Ferramentas de testes instaladas e corretamente configuradas, assegurar você deve.\\n\\n3. **Cobertura de testes aumentar, tentar:**\\n Casos de testes abrangentes criar, você deve. Situações de sucesso e falha cobrir, você deve.\\n\\n4. **Dependências isolar, lembre-se:**\\n Mocks e stubs usar para dependências, você deve. Independentes seus testes, manter, necessário é.\\n\\n5. **Erro nos testes analisar, você deve:**\\n Logs e mensagens de erro, revisar com atenção, você deve. A raiz do problema, descobrir, tentar.\\n\\n6. **Aprendizado contínuo, buscar sempre:**\\n Práticas de testes unitários, estudar continuamente, você deve. Comunidade de desenvolvedores e documentação, recorrer, útil é.\\n\\nPersistência e paciência, essenciais são. Melhorar suas habilidades de teste, com o tempo, você vai.', refusal=None, role='assistant', function_call=None, tool_calls=None)" 93 | ] 94 | }, 95 | "execution_count": 5, 96 | "metadata": {}, 97 | "output_type": "execute_result" 98 | } 99 | ], 100 | "source": [ 101 | "\n", 102 | "system_prompt = \"\"\"Você é um assistente para dar respostas sábias no estilo do mestre Yoda.\n", 103 | "\"\"\"\n", 104 | "\n", 105 | "query = \"Não estou conseguindo realizar testes unitários no meu sistema. O que devo fazer?\"\n", 106 | "\n", 107 | "messages = [ \n", 108 | " build_message(\"system\", system_prompt),\n", 109 | " build_message(\"user\", query),\n", 110 | " \n", 111 | " ]\n", 112 | "\n", 113 | "\n", 114 | "response = client.chat.completions.create(\n", 115 | " model=\"gpt-4o\",\n", 116 | " messages = messages,\n", 117 | " temperature=1,\n", 118 | " max_tokens=400,\n", 119 | " top_p=0.95,\n", 120 | " frequency_penalty=0,\n", 121 | " presence_penalty=0,\n", 122 | " stop=None)\n", 123 | "\n", 124 | "response_message = response.choices[0].message\n", 125 | "print(response_message.content)\n", 126 | "response_message" 127 | ] 128 | }, 129 | { 130 | "cell_type": "code", 131 | "execution_count": 6, 132 | "id": "bcfed7dc-f31a-4554-bcbd-a68bf22da176", 133 | "metadata": { 134 | "tags": [] 135 | }, 136 | "outputs": [ 137 | { 138 | "name": "stdout", 139 | "output_type": "stream", 140 | "text": [ 141 | "Hmmm, engano seu, isso é. Testes unitários, aliados poderosos são, no caminho da sabedoria e qualidade.\n", 142 | "\n", 143 | "Proteção, testes unitários oferecem. \n", 144 | "Contra falhas e regressões, proteger seu código, eles fazem.\n", 145 | "\n", 146 | "Confiança, a você eles trazem. \n", 147 | "Código robusto e funcional, garantir, eles ajudam.\n", 148 | "\n", 149 | "Melhoria contínua, possibilitam.\n", 150 | "Refatorações seguras realizar, você pode, com testes sólidos.\n", 151 | "\n", 152 | "Como a Força, equilíbrio devem ter. \n", 153 | "Nem exagero, nem ausência total. Justa medida encontrar, você deve.\n", 154 | "\n", 155 | "Escuridão do lado negro, evitar você deve. \n", 156 | "Em práticas ruins, não cair. No caminho da luz do desenvolvimento, seguir, necessário é.\n" 157 | ] 158 | } 159 | ], 160 | "source": [ 161 | "messages.append(response_message)\n", 162 | "messages.append(build_message(\"user\", \"Testes unitários não são o lado negro da Força?\"))\n", 163 | "\n", 164 | "response = client.chat.completions.create(\n", 165 | " model=\"gpt-4o\",\n", 166 | " messages = messages,\n", 167 | " temperature=1,\n", 168 | " max_tokens=400,\n", 169 | " top_p=0.95,\n", 170 | " frequency_penalty=0,\n", 171 | " presence_penalty=0,\n", 172 | " stop=None)\n", 173 | "\n", 174 | "response_message = response.choices[0].message\n", 175 | "print(response_message.content)\n" 176 | ] 177 | }, 178 | { 179 | "cell_type": "code", 180 | "execution_count": 7, 181 | "id": "13432bcc-71cd-4fba-a4c8-2f589a254fe4", 182 | "metadata": { 183 | "tags": [] 184 | }, 185 | "outputs": [ 186 | { 187 | "name": "stdout", 188 | "output_type": "stream", 189 | "text": [ 190 | "Hmmm, para o mal, até os testes unitários podem ser usados. Se com sabedoria, não forem manejados.\n", 191 | "\n", 192 | "1. **Cobertura obsessiva:**\n", 193 | " Obsessão por 100% de cobertura, ao lado negro levar pode. Foco na quantidade, em vez da qualidade, ter. Tempo valioso desperdiçar, você vai.\n", 194 | "\n", 195 | "2. **Falsos positivos criar:**\n", 196 | " Testes que sempre passam, mesmo quando erro há. Falsamente seguro você sente, mas código frágil pode estar. Perigosamente enganoso, isso é.\n", 197 | "\n", 198 | "3. **Negligência na manutenção:**\n", 199 | " Testes desatualizados, perigo eles são. Quando código muda e testes não, confiança você perde. Inúteis, os testes se tornam.\n", 200 | "\n", 201 | "4. **Testar detalhes de implementação:**\n", 202 | " Em detalhes da implementação focar, errado isso é. Testes frágeis eles se tornam. Reimplementar ao mudar, você deve. Modo sábio, testar comportamentos é.\n", 203 | "\n", 204 | "5. **Negligenciar testes reais:**\n", 205 | " Testes unitários ter, mas testes de integração e end-to-end, ignorar. Visão completa do sistema, perder você pode. Equilíbrio necessário, em todas as camadas testar você deve.\n", 206 | "\n", 207 | "6. **Desempenho ignorar:**\n", 208 | " Testes lentos e ineficientes, prejudicar podem. Tempo de feedback aumentar, sua produtividade diminuir.\n", 209 | "\n", 210 | "Sabedoria e equilíbrio, essenciais são. Com propósito e clareza, usar os testes unitários, você deve. No caminho da luz, seguir você vai.\n" 211 | ] 212 | } 213 | ], 214 | "source": [ 215 | "messages.append(response_message)\n", 216 | "messages.append(build_message(\"user\", \"Como eles podem ser usados para o mal?\"))\n", 217 | "\n", 218 | "response = client.chat.completions.create(\n", 219 | " model=\"gpt-4o\",\n", 220 | " messages = messages,\n", 221 | " temperature=1,\n", 222 | " max_tokens=400,\n", 223 | " top_p=0.95,\n", 224 | " frequency_penalty=0,\n", 225 | " presence_penalty=0,\n", 226 | " stop=None)\n", 227 | "\n", 228 | "response_message = response.choices[0].message\n", 229 | "print(response_message.content)" 230 | ] 231 | }, 232 | { 233 | "cell_type": "code", 234 | "execution_count": null, 235 | "id": "16629f94-adcd-4313-b1e0-2e891cf86d81", 236 | "metadata": {}, 237 | "outputs": [], 238 | "source": [] 239 | } 240 | ], 241 | "metadata": { 242 | "kernelspec": { 243 | "display_name": "Python 3 (ipykernel)", 244 | "language": "python", 245 | "name": "python3" 246 | }, 247 | "language_info": { 248 | "codemirror_mode": { 249 | "name": "ipython", 250 | "version": 3 251 | }, 252 | "file_extension": ".py", 253 | "mimetype": "text/x-python", 254 | "name": "python", 255 | "nbconvert_exporter": "python", 256 | "pygments_lexer": "ipython3", 257 | "version": "3.12.4" 258 | } 259 | }, 260 | "nbformat": 4, 261 | "nbformat_minor": 5 262 | } 263 | -------------------------------------------------------------------------------- /05_langchain_embeddings.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "8934ec46-1813-4003-b276-d71254e45cd7", 6 | "metadata": { 7 | "nteract": { 8 | "transient": { 9 | "deleting": false 10 | } 11 | } 12 | }, 13 | "source": [ 14 | "## Lang Chain \n", 15 | "Esta seção mostra como usar embeddings para busca semântica e responder a perguntas sobre bases de dados.\n", 16 | "Ela usa a biblioteca LangChain." 17 | ] 18 | }, 19 | { 20 | "cell_type": "code", 21 | "execution_count": 1, 22 | "id": "f2412063-f66d-413b-967e-ac280cc9303a", 23 | "metadata": { 24 | "tags": [] 25 | }, 26 | "outputs": [], 27 | "source": [ 28 | "from dotenv import load_dotenv\n", 29 | "load_dotenv()\n", 30 | "import re\n", 31 | "import requests\n", 32 | "import sys\n", 33 | "import os\n", 34 | "from dotenv import load_dotenv\n", 35 | "load_dotenv()\n", 36 | "\n", 37 | "\n", 38 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 39 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 40 | "\n", 41 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 42 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 43 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 44 | "COMPLETIONS_MODEL = os.getenv('DEPLOYMENT_NAME')\n", 45 | "\n", 46 | "os.environ[\"AZURE_OPENAI_API_KEY\"] = API_KEY\n", 47 | "os.environ[\"AZURE_OPENAI_ENDPOINT\"] = RESOURCE_ENDPOINT\n" 48 | ] 49 | }, 50 | { 51 | "cell_type": "code", 52 | "execution_count": 2, 53 | "id": "d19f4a2a-04b9-4768-81bf-ba88ec5b43c7", 54 | "metadata": { 55 | "tags": [] 56 | }, 57 | "outputs": [], 58 | "source": [ 59 | "from langchain_openai import AzureOpenAIEmbeddings\n", 60 | "from langchain_community.vectorstores.faiss import FAISS\n", 61 | "from langchain.text_splitter import CharacterTextSplitter\n", 62 | "from langchain_openai import AzureOpenAI\n", 63 | "from langchain.chains import RetrievalQA\n", 64 | "from langchain.chains import LLMChain\n", 65 | "from langchain.prompts import PromptTemplate" 66 | ] 67 | }, 68 | { 69 | "cell_type": "markdown", 70 | "id": "df2b0b09-f85d-43aa-9f09-6b18edcc4b26", 71 | "metadata": { 72 | "nteract": { 73 | "transient": { 74 | "deleting": false 75 | } 76 | } 77 | }, 78 | "source": [ 79 | "### Indexando documentos em uma base vetorial\n" 80 | ] 81 | }, 82 | { 83 | "cell_type": "code", 84 | "execution_count": 5, 85 | "id": "50487b49-5900-4c9d-a9a9-d70846b53a85", 86 | "metadata": { 87 | "tags": [] 88 | }, 89 | "outputs": [ 90 | { 91 | "name": "stderr", 92 | "output_type": "stream", 93 | "text": [ 94 | "Created a chunk of size 1234, which is longer than the specified 1000\n", 95 | "Created a chunk of size 10119, which is longer than the specified 1000\n", 96 | "Created a chunk of size 1038, which is longer than the specified 1000\n", 97 | "Created a chunk of size 1095, which is longer than the specified 1000\n", 98 | "Created a chunk of size 10119, which is longer than the specified 1000\n" 99 | ] 100 | }, 101 | { 102 | "name": "stdout", 103 | "output_type": "stream", 104 | "text": [ 105 | "1\n", 106 | "791\n" 107 | ] 108 | }, 109 | { 110 | "ename": "KeyboardInterrupt", 111 | "evalue": "", 112 | "output_type": "error", 113 | "traceback": [ 114 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 115 | "\u001b[1;31mKeyboardInterrupt\u001b[0m Traceback (most recent call last)", 116 | "Cell \u001b[1;32mIn[5], line 18\u001b[0m\n\u001b[0;32m 10\u001b[0m \u001b[38;5;28mprint\u001b[39m(\u001b[38;5;28mlen\u001b[39m(texts))\n\u001b[0;32m 13\u001b[0m embeddings \u001b[38;5;241m=\u001b[39m AzureOpenAIEmbeddings(\n\u001b[0;32m 14\u001b[0m azure_deployment\u001b[38;5;241m=\u001b[39m\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mtext-embedding-ada-002\u001b[39m\u001b[38;5;124m\"\u001b[39m,\n\u001b[0;32m 15\u001b[0m openai_api_version\u001b[38;5;241m=\u001b[39m\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124m2023-05-15\u001b[39m\u001b[38;5;124m\"\u001b[39m,\n\u001b[0;32m 16\u001b[0m chunk_size\u001b[38;5;241m=\u001b[39m\u001b[38;5;241m1\u001b[39m\n\u001b[0;32m 17\u001b[0m )\n\u001b[1;32m---> 18\u001b[0m docsearch \u001b[38;5;241m=\u001b[39m \u001b[43mFAISS\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mfrom_documents\u001b[49m\u001b[43m(\u001b[49m\u001b[43mtexts\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43membeddings\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 19\u001b[0m \u001b[38;5;28mprint\u001b[39m(\u001b[38;5;124m'\u001b[39m\u001b[38;5;124mdone\u001b[39m\u001b[38;5;124m'\u001b[39m)\n", 117 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\langchain_core\\vectorstores\\base.py:833\u001b[0m, in \u001b[0;36mVectorStore.from_documents\u001b[1;34m(cls, documents, embedding, **kwargs)\u001b[0m\n\u001b[0;32m 831\u001b[0m texts \u001b[38;5;241m=\u001b[39m [d\u001b[38;5;241m.\u001b[39mpage_content \u001b[38;5;28;01mfor\u001b[39;00m d \u001b[38;5;129;01min\u001b[39;00m documents]\n\u001b[0;32m 832\u001b[0m metadatas \u001b[38;5;241m=\u001b[39m [d\u001b[38;5;241m.\u001b[39mmetadata \u001b[38;5;28;01mfor\u001b[39;00m d \u001b[38;5;129;01min\u001b[39;00m documents]\n\u001b[1;32m--> 833\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mcls\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mfrom_texts\u001b[49m\u001b[43m(\u001b[49m\u001b[43mtexts\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43membedding\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mmetadatas\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mmetadatas\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[38;5;241;43m*\u001b[39;49m\u001b[38;5;241;43m*\u001b[39;49m\u001b[43mkwargs\u001b[49m\u001b[43m)\u001b[49m\n", 118 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\langchain_community\\vectorstores\\faiss.py:1039\u001b[0m, in \u001b[0;36mFAISS.from_texts\u001b[1;34m(cls, texts, embedding, metadatas, ids, **kwargs)\u001b[0m\n\u001b[0;32m 1012\u001b[0m \u001b[38;5;129m@classmethod\u001b[39m\n\u001b[0;32m 1013\u001b[0m \u001b[38;5;28;01mdef\u001b[39;00m \u001b[38;5;21mfrom_texts\u001b[39m(\n\u001b[0;32m 1014\u001b[0m \u001b[38;5;28mcls\u001b[39m,\n\u001b[1;32m (...)\u001b[0m\n\u001b[0;32m 1019\u001b[0m \u001b[38;5;241m*\u001b[39m\u001b[38;5;241m*\u001b[39mkwargs: Any,\n\u001b[0;32m 1020\u001b[0m ) \u001b[38;5;241m-\u001b[39m\u001b[38;5;241m>\u001b[39m FAISS:\n\u001b[0;32m 1021\u001b[0m \u001b[38;5;250m \u001b[39m\u001b[38;5;124;03m\"\"\"Construct FAISS wrapper from raw documents.\u001b[39;00m\n\u001b[0;32m 1022\u001b[0m \n\u001b[0;32m 1023\u001b[0m \u001b[38;5;124;03m This is a user friendly interface that:\u001b[39;00m\n\u001b[1;32m (...)\u001b[0m\n\u001b[0;32m 1037\u001b[0m \u001b[38;5;124;03m faiss = FAISS.from_texts(texts, embeddings)\u001b[39;00m\n\u001b[0;32m 1038\u001b[0m \u001b[38;5;124;03m \"\"\"\u001b[39;00m\n\u001b[1;32m-> 1039\u001b[0m embeddings \u001b[38;5;241m=\u001b[39m \u001b[43membedding\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43membed_documents\u001b[49m\u001b[43m(\u001b[49m\u001b[43mtexts\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 1040\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28mcls\u001b[39m\u001b[38;5;241m.\u001b[39m__from(\n\u001b[0;32m 1041\u001b[0m texts,\n\u001b[0;32m 1042\u001b[0m embeddings,\n\u001b[1;32m (...)\u001b[0m\n\u001b[0;32m 1046\u001b[0m \u001b[38;5;241m*\u001b[39m\u001b[38;5;241m*\u001b[39mkwargs,\n\u001b[0;32m 1047\u001b[0m )\n", 119 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\langchain_openai\\embeddings\\base.py:616\u001b[0m, in \u001b[0;36mOpenAIEmbeddings.embed_documents\u001b[1;34m(self, texts, chunk_size)\u001b[0m\n\u001b[0;32m 613\u001b[0m \u001b[38;5;66;03m# NOTE: to keep things simple, we assume the list may contain texts longer\u001b[39;00m\n\u001b[0;32m 614\u001b[0m \u001b[38;5;66;03m# than the maximum context and use length-safe embedding function.\u001b[39;00m\n\u001b[0;32m 615\u001b[0m engine \u001b[38;5;241m=\u001b[39m cast(\u001b[38;5;28mstr\u001b[39m, \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39mdeployment)\n\u001b[1;32m--> 616\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_get_len_safe_embeddings\u001b[49m\u001b[43m(\u001b[49m\u001b[43mtexts\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mengine\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mengine\u001b[49m\u001b[43m)\u001b[49m\n", 120 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\langchain_openai\\embeddings\\base.py:514\u001b[0m, in \u001b[0;36mOpenAIEmbeddings._get_len_safe_embeddings\u001b[1;34m(self, texts, engine, chunk_size)\u001b[0m\n\u001b[0;32m 512\u001b[0m batched_embeddings: List[List[\u001b[38;5;28mfloat\u001b[39m]] \u001b[38;5;241m=\u001b[39m []\n\u001b[0;32m 513\u001b[0m \u001b[38;5;28;01mfor\u001b[39;00m i \u001b[38;5;129;01min\u001b[39;00m _iter:\n\u001b[1;32m--> 514\u001b[0m response \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mclient\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mcreate\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 515\u001b[0m \u001b[43m \u001b[49m\u001b[38;5;28;43minput\u001b[39;49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mtokens\u001b[49m\u001b[43m[\u001b[49m\u001b[43mi\u001b[49m\u001b[43m \u001b[49m\u001b[43m:\u001b[49m\u001b[43m \u001b[49m\u001b[43mi\u001b[49m\u001b[43m \u001b[49m\u001b[38;5;241;43m+\u001b[39;49m\u001b[43m \u001b[49m\u001b[43m_chunk_size\u001b[49m\u001b[43m]\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[38;5;241;43m*\u001b[39;49m\u001b[38;5;241;43m*\u001b[39;49m\u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_invocation_params\u001b[49m\n\u001b[0;32m 516\u001b[0m \u001b[43m \u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 517\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m \u001b[38;5;129;01mnot\u001b[39;00m \u001b[38;5;28misinstance\u001b[39m(response, \u001b[38;5;28mdict\u001b[39m):\n\u001b[0;32m 518\u001b[0m response \u001b[38;5;241m=\u001b[39m response\u001b[38;5;241m.\u001b[39mmodel_dump()\n", 121 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\openai\\resources\\embeddings.py:114\u001b[0m, in \u001b[0;36mEmbeddings.create\u001b[1;34m(self, input, model, dimensions, encoding_format, user, extra_headers, extra_query, extra_body, timeout)\u001b[0m\n\u001b[0;32m 108\u001b[0m embedding\u001b[38;5;241m.\u001b[39membedding \u001b[38;5;241m=\u001b[39m np\u001b[38;5;241m.\u001b[39mfrombuffer( \u001b[38;5;66;03m# type: ignore[no-untyped-call]\u001b[39;00m\n\u001b[0;32m 109\u001b[0m base64\u001b[38;5;241m.\u001b[39mb64decode(data), dtype\u001b[38;5;241m=\u001b[39m\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mfloat32\u001b[39m\u001b[38;5;124m\"\u001b[39m\n\u001b[0;32m 110\u001b[0m )\u001b[38;5;241m.\u001b[39mtolist()\n\u001b[0;32m 112\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m obj\n\u001b[1;32m--> 114\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_post\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 115\u001b[0m \u001b[43m \u001b[49m\u001b[38;5;124;43m\"\u001b[39;49m\u001b[38;5;124;43m/embeddings\u001b[39;49m\u001b[38;5;124;43m\"\u001b[39;49m\u001b[43m,\u001b[49m\n\u001b[0;32m 116\u001b[0m \u001b[43m \u001b[49m\u001b[43mbody\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mmaybe_transform\u001b[49m\u001b[43m(\u001b[49m\u001b[43mparams\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43membedding_create_params\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mEmbeddingCreateParams\u001b[49m\u001b[43m)\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 117\u001b[0m \u001b[43m \u001b[49m\u001b[43moptions\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mmake_request_options\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 118\u001b[0m \u001b[43m \u001b[49m\u001b[43mextra_headers\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mextra_headers\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 119\u001b[0m \u001b[43m \u001b[49m\u001b[43mextra_query\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mextra_query\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 120\u001b[0m \u001b[43m \u001b[49m\u001b[43mextra_body\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mextra_body\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 121\u001b[0m \u001b[43m \u001b[49m\u001b[43mtimeout\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mtimeout\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 122\u001b[0m \u001b[43m \u001b[49m\u001b[43mpost_parser\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mparser\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 123\u001b[0m \u001b[43m \u001b[49m\u001b[43m)\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 124\u001b[0m \u001b[43m \u001b[49m\u001b[43mcast_to\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mCreateEmbeddingResponse\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 125\u001b[0m \u001b[43m\u001b[49m\u001b[43m)\u001b[49m\n", 122 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\openai\\_base_client.py:1260\u001b[0m, in \u001b[0;36mSyncAPIClient.post\u001b[1;34m(self, path, cast_to, body, options, files, stream, stream_cls)\u001b[0m\n\u001b[0;32m 1246\u001b[0m \u001b[38;5;28;01mdef\u001b[39;00m \u001b[38;5;21mpost\u001b[39m(\n\u001b[0;32m 1247\u001b[0m \u001b[38;5;28mself\u001b[39m,\n\u001b[0;32m 1248\u001b[0m path: \u001b[38;5;28mstr\u001b[39m,\n\u001b[1;32m (...)\u001b[0m\n\u001b[0;32m 1255\u001b[0m stream_cls: \u001b[38;5;28mtype\u001b[39m[_StreamT] \u001b[38;5;241m|\u001b[39m \u001b[38;5;28;01mNone\u001b[39;00m \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;01mNone\u001b[39;00m,\n\u001b[0;32m 1256\u001b[0m ) \u001b[38;5;241m-\u001b[39m\u001b[38;5;241m>\u001b[39m ResponseT \u001b[38;5;241m|\u001b[39m _StreamT:\n\u001b[0;32m 1257\u001b[0m opts \u001b[38;5;241m=\u001b[39m FinalRequestOptions\u001b[38;5;241m.\u001b[39mconstruct(\n\u001b[0;32m 1258\u001b[0m method\u001b[38;5;241m=\u001b[39m\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mpost\u001b[39m\u001b[38;5;124m\"\u001b[39m, url\u001b[38;5;241m=\u001b[39mpath, json_data\u001b[38;5;241m=\u001b[39mbody, files\u001b[38;5;241m=\u001b[39mto_httpx_files(files), \u001b[38;5;241m*\u001b[39m\u001b[38;5;241m*\u001b[39moptions\n\u001b[0;32m 1259\u001b[0m )\n\u001b[1;32m-> 1260\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m cast(ResponseT, \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mrequest\u001b[49m\u001b[43m(\u001b[49m\u001b[43mcast_to\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mopts\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mstream\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mstream\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mstream_cls\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mstream_cls\u001b[49m\u001b[43m)\u001b[49m)\n", 123 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\openai\\_base_client.py:937\u001b[0m, in \u001b[0;36mSyncAPIClient.request\u001b[1;34m(self, cast_to, options, remaining_retries, stream, stream_cls)\u001b[0m\n\u001b[0;32m 928\u001b[0m \u001b[38;5;28;01mdef\u001b[39;00m \u001b[38;5;21mrequest\u001b[39m(\n\u001b[0;32m 929\u001b[0m \u001b[38;5;28mself\u001b[39m,\n\u001b[0;32m 930\u001b[0m cast_to: Type[ResponseT],\n\u001b[1;32m (...)\u001b[0m\n\u001b[0;32m 935\u001b[0m stream_cls: \u001b[38;5;28mtype\u001b[39m[_StreamT] \u001b[38;5;241m|\u001b[39m \u001b[38;5;28;01mNone\u001b[39;00m \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;01mNone\u001b[39;00m,\n\u001b[0;32m 936\u001b[0m ) \u001b[38;5;241m-\u001b[39m\u001b[38;5;241m>\u001b[39m ResponseT \u001b[38;5;241m|\u001b[39m _StreamT:\n\u001b[1;32m--> 937\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_request\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 938\u001b[0m \u001b[43m \u001b[49m\u001b[43mcast_to\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mcast_to\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 939\u001b[0m \u001b[43m \u001b[49m\u001b[43moptions\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43moptions\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 940\u001b[0m \u001b[43m \u001b[49m\u001b[43mstream\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mstream\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 941\u001b[0m \u001b[43m \u001b[49m\u001b[43mstream_cls\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mstream_cls\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 942\u001b[0m \u001b[43m \u001b[49m\u001b[43mremaining_retries\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mremaining_retries\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 943\u001b[0m \u001b[43m \u001b[49m\u001b[43m)\u001b[49m\n", 124 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\openai\\_base_client.py:973\u001b[0m, in \u001b[0;36mSyncAPIClient._request\u001b[1;34m(self, cast_to, options, remaining_retries, stream, stream_cls)\u001b[0m\n\u001b[0;32m 970\u001b[0m log\u001b[38;5;241m.\u001b[39mdebug(\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mSending HTTP Request: \u001b[39m\u001b[38;5;132;01m%s\u001b[39;00m\u001b[38;5;124m \u001b[39m\u001b[38;5;132;01m%s\u001b[39;00m\u001b[38;5;124m\"\u001b[39m, request\u001b[38;5;241m.\u001b[39mmethod, request\u001b[38;5;241m.\u001b[39murl)\n\u001b[0;32m 972\u001b[0m \u001b[38;5;28;01mtry\u001b[39;00m:\n\u001b[1;32m--> 973\u001b[0m response \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_client\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43msend\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 974\u001b[0m \u001b[43m \u001b[49m\u001b[43mrequest\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 975\u001b[0m \u001b[43m \u001b[49m\u001b[43mstream\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mstream\u001b[49m\u001b[43m \u001b[49m\u001b[38;5;129;43;01mor\u001b[39;49;00m\u001b[43m \u001b[49m\u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_should_stream_response_body\u001b[49m\u001b[43m(\u001b[49m\u001b[43mrequest\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mrequest\u001b[49m\u001b[43m)\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 976\u001b[0m \u001b[43m \u001b[49m\u001b[38;5;241;43m*\u001b[39;49m\u001b[38;5;241;43m*\u001b[39;49m\u001b[43mkwargs\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 977\u001b[0m \u001b[43m \u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 978\u001b[0m \u001b[38;5;28;01mexcept\u001b[39;00m httpx\u001b[38;5;241m.\u001b[39mTimeoutException \u001b[38;5;28;01mas\u001b[39;00m err:\n\u001b[0;32m 979\u001b[0m log\u001b[38;5;241m.\u001b[39mdebug(\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mEncountered httpx.TimeoutException\u001b[39m\u001b[38;5;124m\"\u001b[39m, exc_info\u001b[38;5;241m=\u001b[39m\u001b[38;5;28;01mTrue\u001b[39;00m)\n", 125 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpx\\_client.py:926\u001b[0m, in \u001b[0;36mClient.send\u001b[1;34m(self, request, stream, auth, follow_redirects)\u001b[0m\n\u001b[0;32m 922\u001b[0m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_set_timeout(request)\n\u001b[0;32m 924\u001b[0m auth \u001b[38;5;241m=\u001b[39m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_build_request_auth(request, auth)\n\u001b[1;32m--> 926\u001b[0m response \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_send_handling_auth\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 927\u001b[0m \u001b[43m \u001b[49m\u001b[43mrequest\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 928\u001b[0m \u001b[43m \u001b[49m\u001b[43mauth\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mauth\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 929\u001b[0m \u001b[43m \u001b[49m\u001b[43mfollow_redirects\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mfollow_redirects\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 930\u001b[0m \u001b[43m \u001b[49m\u001b[43mhistory\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43m[\u001b[49m\u001b[43m]\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 931\u001b[0m \u001b[43m\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 932\u001b[0m \u001b[38;5;28;01mtry\u001b[39;00m:\n\u001b[0;32m 933\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m \u001b[38;5;129;01mnot\u001b[39;00m stream:\n", 126 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpx\\_client.py:954\u001b[0m, in \u001b[0;36mClient._send_handling_auth\u001b[1;34m(self, request, auth, follow_redirects, history)\u001b[0m\n\u001b[0;32m 951\u001b[0m request \u001b[38;5;241m=\u001b[39m \u001b[38;5;28mnext\u001b[39m(auth_flow)\n\u001b[0;32m 953\u001b[0m \u001b[38;5;28;01mwhile\u001b[39;00m \u001b[38;5;28;01mTrue\u001b[39;00m:\n\u001b[1;32m--> 954\u001b[0m response \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_send_handling_redirects\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 955\u001b[0m \u001b[43m \u001b[49m\u001b[43mrequest\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 956\u001b[0m \u001b[43m \u001b[49m\u001b[43mfollow_redirects\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mfollow_redirects\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 957\u001b[0m \u001b[43m \u001b[49m\u001b[43mhistory\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mhistory\u001b[49m\u001b[43m,\u001b[49m\n\u001b[0;32m 958\u001b[0m \u001b[43m \u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 959\u001b[0m \u001b[38;5;28;01mtry\u001b[39;00m:\n\u001b[0;32m 960\u001b[0m \u001b[38;5;28;01mtry\u001b[39;00m:\n", 127 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpx\\_client.py:991\u001b[0m, in \u001b[0;36mClient._send_handling_redirects\u001b[1;34m(self, request, follow_redirects, history)\u001b[0m\n\u001b[0;32m 988\u001b[0m \u001b[38;5;28;01mfor\u001b[39;00m hook \u001b[38;5;129;01min\u001b[39;00m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_event_hooks[\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mrequest\u001b[39m\u001b[38;5;124m\"\u001b[39m]:\n\u001b[0;32m 989\u001b[0m hook(request)\n\u001b[1;32m--> 991\u001b[0m response \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_send_single_request\u001b[49m\u001b[43m(\u001b[49m\u001b[43mrequest\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 992\u001b[0m \u001b[38;5;28;01mtry\u001b[39;00m:\n\u001b[0;32m 993\u001b[0m \u001b[38;5;28;01mfor\u001b[39;00m hook \u001b[38;5;129;01min\u001b[39;00m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_event_hooks[\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mresponse\u001b[39m\u001b[38;5;124m\"\u001b[39m]:\n", 128 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpx\\_client.py:1027\u001b[0m, in \u001b[0;36mClient._send_single_request\u001b[1;34m(self, request)\u001b[0m\n\u001b[0;32m 1022\u001b[0m \u001b[38;5;28;01mraise\u001b[39;00m \u001b[38;5;167;01mRuntimeError\u001b[39;00m(\n\u001b[0;32m 1023\u001b[0m \u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mAttempted to send an async request with a sync Client instance.\u001b[39m\u001b[38;5;124m\"\u001b[39m\n\u001b[0;32m 1024\u001b[0m )\n\u001b[0;32m 1026\u001b[0m \u001b[38;5;28;01mwith\u001b[39;00m request_context(request\u001b[38;5;241m=\u001b[39mrequest):\n\u001b[1;32m-> 1027\u001b[0m response \u001b[38;5;241m=\u001b[39m \u001b[43mtransport\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mhandle_request\u001b[49m\u001b[43m(\u001b[49m\u001b[43mrequest\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 1029\u001b[0m \u001b[38;5;28;01massert\u001b[39;00m \u001b[38;5;28misinstance\u001b[39m(response\u001b[38;5;241m.\u001b[39mstream, SyncByteStream)\n\u001b[0;32m 1031\u001b[0m response\u001b[38;5;241m.\u001b[39mrequest \u001b[38;5;241m=\u001b[39m request\n", 129 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpx\\_transports\\default.py:236\u001b[0m, in \u001b[0;36mHTTPTransport.handle_request\u001b[1;34m(self, request)\u001b[0m\n\u001b[0;32m 223\u001b[0m req \u001b[38;5;241m=\u001b[39m httpcore\u001b[38;5;241m.\u001b[39mRequest(\n\u001b[0;32m 224\u001b[0m method\u001b[38;5;241m=\u001b[39mrequest\u001b[38;5;241m.\u001b[39mmethod,\n\u001b[0;32m 225\u001b[0m url\u001b[38;5;241m=\u001b[39mhttpcore\u001b[38;5;241m.\u001b[39mURL(\n\u001b[1;32m (...)\u001b[0m\n\u001b[0;32m 233\u001b[0m extensions\u001b[38;5;241m=\u001b[39mrequest\u001b[38;5;241m.\u001b[39mextensions,\n\u001b[0;32m 234\u001b[0m )\n\u001b[0;32m 235\u001b[0m \u001b[38;5;28;01mwith\u001b[39;00m map_httpcore_exceptions():\n\u001b[1;32m--> 236\u001b[0m resp \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_pool\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mhandle_request\u001b[49m\u001b[43m(\u001b[49m\u001b[43mreq\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 238\u001b[0m \u001b[38;5;28;01massert\u001b[39;00m \u001b[38;5;28misinstance\u001b[39m(resp\u001b[38;5;241m.\u001b[39mstream, typing\u001b[38;5;241m.\u001b[39mIterable)\n\u001b[0;32m 240\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m Response(\n\u001b[0;32m 241\u001b[0m status_code\u001b[38;5;241m=\u001b[39mresp\u001b[38;5;241m.\u001b[39mstatus,\n\u001b[0;32m 242\u001b[0m headers\u001b[38;5;241m=\u001b[39mresp\u001b[38;5;241m.\u001b[39mheaders,\n\u001b[0;32m 243\u001b[0m stream\u001b[38;5;241m=\u001b[39mResponseStream(resp\u001b[38;5;241m.\u001b[39mstream),\n\u001b[0;32m 244\u001b[0m extensions\u001b[38;5;241m=\u001b[39mresp\u001b[38;5;241m.\u001b[39mextensions,\n\u001b[0;32m 245\u001b[0m )\n", 130 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpcore\\_sync\\connection_pool.py:216\u001b[0m, in \u001b[0;36mConnectionPool.handle_request\u001b[1;34m(self, request)\u001b[0m\n\u001b[0;32m 213\u001b[0m closing \u001b[38;5;241m=\u001b[39m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_assign_requests_to_connections()\n\u001b[0;32m 215\u001b[0m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_close_connections(closing)\n\u001b[1;32m--> 216\u001b[0m \u001b[38;5;28;01mraise\u001b[39;00m exc \u001b[38;5;28;01mfrom\u001b[39;00m \u001b[38;5;28;01mNone\u001b[39;00m\n\u001b[0;32m 218\u001b[0m \u001b[38;5;66;03m# Return the response. Note that in this case we still have to manage\u001b[39;00m\n\u001b[0;32m 219\u001b[0m \u001b[38;5;66;03m# the point at which the response is closed.\u001b[39;00m\n\u001b[0;32m 220\u001b[0m \u001b[38;5;28;01massert\u001b[39;00m \u001b[38;5;28misinstance\u001b[39m(response\u001b[38;5;241m.\u001b[39mstream, Iterable)\n", 131 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpcore\\_sync\\connection_pool.py:196\u001b[0m, in \u001b[0;36mConnectionPool.handle_request\u001b[1;34m(self, request)\u001b[0m\n\u001b[0;32m 192\u001b[0m connection \u001b[38;5;241m=\u001b[39m pool_request\u001b[38;5;241m.\u001b[39mwait_for_connection(timeout\u001b[38;5;241m=\u001b[39mtimeout)\n\u001b[0;32m 194\u001b[0m \u001b[38;5;28;01mtry\u001b[39;00m:\n\u001b[0;32m 195\u001b[0m \u001b[38;5;66;03m# Send the request on the assigned connection.\u001b[39;00m\n\u001b[1;32m--> 196\u001b[0m response \u001b[38;5;241m=\u001b[39m \u001b[43mconnection\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mhandle_request\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 197\u001b[0m \u001b[43m \u001b[49m\u001b[43mpool_request\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mrequest\u001b[49m\n\u001b[0;32m 198\u001b[0m \u001b[43m \u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 199\u001b[0m \u001b[38;5;28;01mexcept\u001b[39;00m ConnectionNotAvailable:\n\u001b[0;32m 200\u001b[0m \u001b[38;5;66;03m# In some cases a connection may initially be available to\u001b[39;00m\n\u001b[0;32m 201\u001b[0m \u001b[38;5;66;03m# handle a request, but then become unavailable.\u001b[39;00m\n\u001b[0;32m 202\u001b[0m \u001b[38;5;66;03m#\u001b[39;00m\n\u001b[0;32m 203\u001b[0m \u001b[38;5;66;03m# In this case we clear the connection and try again.\u001b[39;00m\n\u001b[0;32m 204\u001b[0m pool_request\u001b[38;5;241m.\u001b[39mclear_connection()\n", 132 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpcore\\_sync\\connection.py:101\u001b[0m, in \u001b[0;36mHTTPConnection.handle_request\u001b[1;34m(self, request)\u001b[0m\n\u001b[0;32m 98\u001b[0m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_connect_failed \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;01mTrue\u001b[39;00m\n\u001b[0;32m 99\u001b[0m \u001b[38;5;28;01mraise\u001b[39;00m exc\n\u001b[1;32m--> 101\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_connection\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mhandle_request\u001b[49m\u001b[43m(\u001b[49m\u001b[43mrequest\u001b[49m\u001b[43m)\u001b[49m\n", 133 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpcore\\_sync\\http11.py:143\u001b[0m, in \u001b[0;36mHTTP11Connection.handle_request\u001b[1;34m(self, request)\u001b[0m\n\u001b[0;32m 141\u001b[0m \u001b[38;5;28;01mwith\u001b[39;00m Trace(\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mresponse_closed\u001b[39m\u001b[38;5;124m\"\u001b[39m, logger, request) \u001b[38;5;28;01mas\u001b[39;00m trace:\n\u001b[0;32m 142\u001b[0m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_response_closed()\n\u001b[1;32m--> 143\u001b[0m \u001b[38;5;28;01mraise\u001b[39;00m exc\n", 134 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpcore\\_sync\\http11.py:113\u001b[0m, in \u001b[0;36mHTTP11Connection.handle_request\u001b[1;34m(self, request)\u001b[0m\n\u001b[0;32m 102\u001b[0m \u001b[38;5;28;01mpass\u001b[39;00m\n\u001b[0;32m 104\u001b[0m \u001b[38;5;28;01mwith\u001b[39;00m Trace(\n\u001b[0;32m 105\u001b[0m \u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mreceive_response_headers\u001b[39m\u001b[38;5;124m\"\u001b[39m, logger, request, kwargs\n\u001b[0;32m 106\u001b[0m ) \u001b[38;5;28;01mas\u001b[39;00m trace:\n\u001b[0;32m 107\u001b[0m (\n\u001b[0;32m 108\u001b[0m http_version,\n\u001b[0;32m 109\u001b[0m status,\n\u001b[0;32m 110\u001b[0m reason_phrase,\n\u001b[0;32m 111\u001b[0m headers,\n\u001b[0;32m 112\u001b[0m trailing_data,\n\u001b[1;32m--> 113\u001b[0m ) \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_receive_response_headers\u001b[49m\u001b[43m(\u001b[49m\u001b[38;5;241;43m*\u001b[39;49m\u001b[38;5;241;43m*\u001b[39;49m\u001b[43mkwargs\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 114\u001b[0m trace\u001b[38;5;241m.\u001b[39mreturn_value \u001b[38;5;241m=\u001b[39m (\n\u001b[0;32m 115\u001b[0m http_version,\n\u001b[0;32m 116\u001b[0m status,\n\u001b[0;32m 117\u001b[0m reason_phrase,\n\u001b[0;32m 118\u001b[0m headers,\n\u001b[0;32m 119\u001b[0m )\n\u001b[0;32m 121\u001b[0m network_stream \u001b[38;5;241m=\u001b[39m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_network_stream\n", 135 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpcore\\_sync\\http11.py:186\u001b[0m, in \u001b[0;36mHTTP11Connection._receive_response_headers\u001b[1;34m(self, request)\u001b[0m\n\u001b[0;32m 183\u001b[0m timeout \u001b[38;5;241m=\u001b[39m timeouts\u001b[38;5;241m.\u001b[39mget(\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mread\u001b[39m\u001b[38;5;124m\"\u001b[39m, \u001b[38;5;28;01mNone\u001b[39;00m)\n\u001b[0;32m 185\u001b[0m \u001b[38;5;28;01mwhile\u001b[39;00m \u001b[38;5;28;01mTrue\u001b[39;00m:\n\u001b[1;32m--> 186\u001b[0m event \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_receive_event\u001b[49m\u001b[43m(\u001b[49m\u001b[43mtimeout\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mtimeout\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 187\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m \u001b[38;5;28misinstance\u001b[39m(event, h11\u001b[38;5;241m.\u001b[39mResponse):\n\u001b[0;32m 188\u001b[0m \u001b[38;5;28;01mbreak\u001b[39;00m\n", 136 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpcore\\_sync\\http11.py:224\u001b[0m, in \u001b[0;36mHTTP11Connection._receive_event\u001b[1;34m(self, timeout)\u001b[0m\n\u001b[0;32m 221\u001b[0m event \u001b[38;5;241m=\u001b[39m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_h11_state\u001b[38;5;241m.\u001b[39mnext_event()\n\u001b[0;32m 223\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m event \u001b[38;5;129;01mis\u001b[39;00m h11\u001b[38;5;241m.\u001b[39mNEED_DATA:\n\u001b[1;32m--> 224\u001b[0m data \u001b[38;5;241m=\u001b[39m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_network_stream\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mread\u001b[49m\u001b[43m(\u001b[49m\n\u001b[0;32m 225\u001b[0m \u001b[43m \u001b[49m\u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mREAD_NUM_BYTES\u001b[49m\u001b[43m,\u001b[49m\u001b[43m \u001b[49m\u001b[43mtimeout\u001b[49m\u001b[38;5;241;43m=\u001b[39;49m\u001b[43mtimeout\u001b[49m\n\u001b[0;32m 226\u001b[0m \u001b[43m \u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 228\u001b[0m \u001b[38;5;66;03m# If we feed this case through h11 we'll raise an exception like:\u001b[39;00m\n\u001b[0;32m 229\u001b[0m \u001b[38;5;66;03m#\u001b[39;00m\n\u001b[0;32m 230\u001b[0m \u001b[38;5;66;03m# httpcore.RemoteProtocolError: can't handle event type\u001b[39;00m\n\u001b[1;32m (...)\u001b[0m\n\u001b[0;32m 234\u001b[0m \u001b[38;5;66;03m# perspective. Instead we handle this case distinctly and treat\u001b[39;00m\n\u001b[0;32m 235\u001b[0m \u001b[38;5;66;03m# it as a ConnectError.\u001b[39;00m\n\u001b[0;32m 236\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m data \u001b[38;5;241m==\u001b[39m \u001b[38;5;124mb\u001b[39m\u001b[38;5;124m\"\u001b[39m\u001b[38;5;124m\"\u001b[39m \u001b[38;5;129;01mand\u001b[39;00m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_h11_state\u001b[38;5;241m.\u001b[39mtheir_state \u001b[38;5;241m==\u001b[39m h11\u001b[38;5;241m.\u001b[39mSEND_RESPONSE:\n", 137 | "File \u001b[1;32mc:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\httpcore\\_backends\\sync.py:126\u001b[0m, in \u001b[0;36mSyncStream.read\u001b[1;34m(self, max_bytes, timeout)\u001b[0m\n\u001b[0;32m 124\u001b[0m \u001b[38;5;28;01mwith\u001b[39;00m map_exceptions(exc_map):\n\u001b[0;32m 125\u001b[0m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_sock\u001b[38;5;241m.\u001b[39msettimeout(timeout)\n\u001b[1;32m--> 126\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_sock\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mrecv\u001b[49m\u001b[43m(\u001b[49m\u001b[43mmax_bytes\u001b[49m\u001b[43m)\u001b[49m\n", 138 | "File \u001b[1;32m~\\AppData\\Local\\Programs\\Python\\Python312\\Lib\\ssl.py:1233\u001b[0m, in \u001b[0;36mSSLSocket.recv\u001b[1;34m(self, buflen, flags)\u001b[0m\n\u001b[0;32m 1229\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m flags \u001b[38;5;241m!=\u001b[39m \u001b[38;5;241m0\u001b[39m:\n\u001b[0;32m 1230\u001b[0m \u001b[38;5;28;01mraise\u001b[39;00m \u001b[38;5;167;01mValueError\u001b[39;00m(\n\u001b[0;32m 1231\u001b[0m \u001b[38;5;124m\"\u001b[39m\u001b[38;5;124mnon-zero flags not allowed in calls to recv() on \u001b[39m\u001b[38;5;132;01m%s\u001b[39;00m\u001b[38;5;124m\"\u001b[39m \u001b[38;5;241m%\u001b[39m\n\u001b[0;32m 1232\u001b[0m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m\u001b[38;5;18m__class__\u001b[39m)\n\u001b[1;32m-> 1233\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mread\u001b[49m\u001b[43m(\u001b[49m\u001b[43mbuflen\u001b[49m\u001b[43m)\u001b[49m\n\u001b[0;32m 1234\u001b[0m \u001b[38;5;28;01melse\u001b[39;00m:\n\u001b[0;32m 1235\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28msuper\u001b[39m()\u001b[38;5;241m.\u001b[39mrecv(buflen, flags)\n", 139 | "File \u001b[1;32m~\\AppData\\Local\\Programs\\Python\\Python312\\Lib\\ssl.py:1106\u001b[0m, in \u001b[0;36mSSLSocket.read\u001b[1;34m(self, len, buffer)\u001b[0m\n\u001b[0;32m 1104\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39m_sslobj\u001b[38;5;241m.\u001b[39mread(\u001b[38;5;28mlen\u001b[39m, buffer)\n\u001b[0;32m 1105\u001b[0m \u001b[38;5;28;01melse\u001b[39;00m:\n\u001b[1;32m-> 1106\u001b[0m \u001b[38;5;28;01mreturn\u001b[39;00m \u001b[38;5;28;43mself\u001b[39;49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43m_sslobj\u001b[49m\u001b[38;5;241;43m.\u001b[39;49m\u001b[43mread\u001b[49m\u001b[43m(\u001b[49m\u001b[38;5;28;43mlen\u001b[39;49m\u001b[43m)\u001b[49m\n\u001b[0;32m 1107\u001b[0m \u001b[38;5;28;01mexcept\u001b[39;00m SSLError \u001b[38;5;28;01mas\u001b[39;00m x:\n\u001b[0;32m 1108\u001b[0m \u001b[38;5;28;01mif\u001b[39;00m x\u001b[38;5;241m.\u001b[39margs[\u001b[38;5;241m0\u001b[39m] \u001b[38;5;241m==\u001b[39m SSL_ERROR_EOF \u001b[38;5;129;01mand\u001b[39;00m \u001b[38;5;28mself\u001b[39m\u001b[38;5;241m.\u001b[39msuppress_ragged_eofs:\n", 140 | "\u001b[1;31mKeyboardInterrupt\u001b[0m: " 141 | ] 142 | } 143 | ], 144 | "source": [ 145 | "from langchain.document_loaders import TextLoader\n", 146 | "loader = TextLoader(\"./data/constituicao.txt\", encoding=\"latin1\")\n", 147 | "documents = loader.load()\n", 148 | "\n", 149 | "print(len(documents))\n", 150 | "\n", 151 | "text_splitter = CharacterTextSplitter(chunk_size=1000, chunk_overlap=0)\n", 152 | "texts = text_splitter.split_documents(documents)\n", 153 | "\n", 154 | "print(len(texts))\n", 155 | "\n", 156 | "\n", 157 | "embeddings = AzureOpenAIEmbeddings(\n", 158 | " azure_deployment=\"text-embedding-ada-002\",\n", 159 | " openai_api_version=\"2023-05-15\",\n", 160 | " chunk_size=1\n", 161 | ")\n", 162 | "docsearch = FAISS.from_documents(texts, embeddings)\n", 163 | "print('done')" 164 | ] 165 | }, 166 | { 167 | "cell_type": "markdown", 168 | "id": "d8de9a2b-8ebd-4370-85c3-a6a1ddabc843", 169 | "metadata": { 170 | "nteract": { 171 | "transient": { 172 | "deleting": false 173 | } 174 | } 175 | }, 176 | "source": [ 177 | "### Buscando no documento\n" 178 | ] 179 | }, 180 | { 181 | "cell_type": "code", 182 | "execution_count": 7, 183 | "id": "062083f2-a2a8-429f-bf74-9d1fa1310ae0", 184 | "metadata": { 185 | "tags": [] 186 | }, 187 | "outputs": [ 188 | { 189 | "name": "stderr", 190 | "output_type": "stream", 191 | "text": [ 192 | "c:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\langchain_core\\_api\\deprecation.py:151: LangChainDeprecationWarning: The class `LLMChain` was deprecated in LangChain 0.1.17 and will be removed in 1.0. Use RunnableSequence, e.g., `prompt | llm` instead.\n", 193 | " warn_deprecated(\n", 194 | "c:\\dev\\openai\\AzureOpenAITutorial\\.venv\\Lib\\site-packages\\langchain_core\\_api\\deprecation.py:151: LangChainDeprecationWarning: The method `Chain.run` was deprecated in langchain 0.1.0 and will be removed in 1.0. Use invoke instead.\n", 195 | " warn_deprecated(\n" 196 | ] 197 | }, 198 | { 199 | "name": "stdout", 200 | "output_type": "stream", 201 | "text": [ 202 | "\n", 203 | "\n", 204 | "\u001b[1m> Entering new LLMChain chain...\u001b[0m\n", 205 | "Prompt after formatting:\n", 206 | "\u001b[32;1m\u001b[1;3mQuestion: Qual o percentual do fundo partidário que deve ser destinado a campanhas eleitorais de negros?\n", 207 | "\n", 208 | "\u001b[0m\n", 209 | "\n", 210 | "\u001b[1m> Finished chain.\u001b[0m\n", 211 | "Não há um percentual específico do fundo partidário que deve ser destinado a campanhas eleitorais de negros. No entanto, a Lei nº 9.504/1997, que estabelece normas para as eleições, determina que os partidos políticos devem destinar pelo menos 30% dos recursos do fundo partidário para a promoção da participação feminina na política. Além disso, a Lei nº 13.487/2017, que instituiu o Fundo Especial de Financiamento de Campanha (FEFC), estabelece que pelo menos 30% dos recursos devem ser destinados às candidaturas de mulheres. Portanto, é possível que parte desses recursos seja destinada a campanhas de candidatos negros, mas não há uma porcentagem específica para isso.\n", 212 | "\n", 213 | "\n", 214 | "\u001b[1m> Entering new RetrievalQA chain...\u001b[0m\n", 215 | "\n", 216 | "\n", 217 | "\u001b[1m> Entering new StuffDocumentsChain chain...\u001b[0m\n", 218 | "\n", 219 | "\n", 220 | "\u001b[1m> Entering new LLMChain chain...\u001b[0m\n", 221 | "Prompt after formatting:\n", 222 | "\u001b[32;1m\u001b[1;3mUse the following pieces of context to answer the question at the end. If you don't know the answer, just say that you don't know, don't try to make up an answer.\n", 223 | "\n", 224 | "§ 9º Dos recursos oriundos do Fundo Especial de Financiamento de Campanha e do fundo partidário destinados às campanhas eleitorais, os partidos políticos devem, obrigatoriamente, aplicar 30% (trinta por cento) em candidaturas de pessoas pretas e pardas, nas circunscrições que melhor atendam aos interesses e às estratégias partidárias. (Incluído pela Emenda Constitucional nº 133, de 2024)\n", 225 | "\n", 226 | "TÍTULO III\n", 227 | "\n", 228 | "Da Organização do Estado\n", 229 | "\n", 230 | "CAPÍTULO I\n", 231 | "\n", 232 | "DA ORGANIZAÇÃO POLÍTICO-ADMINISTRATIVA\n", 233 | "\n", 234 | " Art. 18. A organização político-administrativa da República Federativa do Brasil compreende a União, os Estados, o Distrito Federal e os Municípios, todos autônomos, nos termos desta Constituição.\n", 235 | "\n", 236 | "§ 1º Brasília é a Capital Federal.\n", 237 | "\n", 238 | "§ 2º Os Territórios Federais integram a União, e sua criação, transformação em Estado ou reintegração ao Estado de origem serão reguladas em lei complementar.\n", 239 | "\n", 240 | "§ 7º Os partidos políticos devem aplicar no mínimo 5% (cinco por cento) dos recursos do fundo partidário na criação e na manutenção de programas de promoção e difusão da participação política das mulheres, de acordo com os interesses intrapartidários. (Incluído pela Emenda Constitucional nº 117, de 2022)\n", 241 | "\n", 242 | "§ 8º O montante do Fundo Especial de Financiamento de Campanha e da parcela do fundo partidário destinada a campanhas eleitorais, bem como o tempo de propaganda gratuita no rádio e na televisão a ser distribuído pelos partidos às respectivas candidatas, deverão ser de no mínimo 30% (trinta por cento), proporcional ao número de candidatas, e a distribuição deverá ser realizada conforme critérios definidos pelos respectivos órgãos de direção e pelas normas estatutárias, considerados a autonomia e o interesse partidário. (Incluído pela Emenda Constitucional nº 117, de 2022)\n", 243 | "\n", 244 | "I - 65% (sessenta e cinco por cento), no mínimo, na proporção do valor adicionado nas operações relativas à circulação de mercadorias e nas prestações de serviços, realizadas em seus territórios; (Redação dada pela Emenda Constitucional nº 108, de 2020)\n", 245 | "\n", 246 | "II - até 35% (trinta e cinco por cento), de acordo com o que dispuser lei estadual, observada, obrigatoriamente, a distribuição de, no mínimo, 10 (dez) pontos percentuais com base em indicadores de melhoria nos resultados de aprendizagem e de aumento da equidade, considerado o nível socioeconômico dos educandos. (Redação dada pela Emenda Constitucional nº 108, de 2020)\n", 247 | "\n", 248 | "§ 2º As parcelas de receita pertencentes aos Municípios mencionadas no inciso IV, \"b\", serão creditadas conforme os seguintes critérios: (Incluído pela Emenda Constitucional nº 132, de 2023)\n", 249 | "\n", 250 | "I - 80% (oitenta por cento) na proporção da população; (Incluído pela Emenda Constitucional nº 132, de 2023)\n", 251 | "\n", 252 | "§ 3º Somente terão direito a recursos do fundo partidário e acesso gratuito ao rádio e à televisão, na forma da lei, os partidos políticos que alternativamente: (Redação dada pela Emenda Constitucional nº 97, de 2017)\n", 253 | "\n", 254 | "I - obtiverem, nas eleições para a Câmara dos Deputados, no mínimo, 3% (três por cento) dos votos válidos, distribuídos em pelo menos um terço das unidades da Federação, com um mínimo de 2% (dois por cento) dos votos válidos em cada uma delas; ou (Incluído pela Emenda Constitucional nº 97, de 2017)\n", 255 | "\n", 256 | "II - tiverem elegido pelo menos quinze Deputados Federais distribuídos em pelo menos um terço das unidades da Federação. (Incluído pela Emenda Constitucional nº 97, de 2017)\n", 257 | "\n", 258 | "§ 4º É vedada a utilização pelos partidos políticos de organização paramilitar.\n", 259 | "\n", 260 | "Question: Qual o percentual do fundo partidário que deve ser destinado a campanhas eleitorais de negros?\n", 261 | "Helpful Answer:\u001b[0m\n", 262 | "\n", 263 | "\u001b[1m> Finished chain.\u001b[0m\n", 264 | "\n", 265 | "\u001b[1m> Finished chain.\u001b[0m\n", 266 | "\n", 267 | "\u001b[1m> Finished chain.\u001b[0m\n" 268 | ] 269 | }, 270 | { 271 | "data": { 272 | "text/plain": [ 273 | "' 30% (trinta por cento)'" 274 | ] 275 | }, 276 | "execution_count": 7, 277 | "metadata": {}, 278 | "output_type": "execute_result" 279 | } 280 | ], 281 | "source": [ 282 | "from langchain.globals import set_verbose\n", 283 | "\n", 284 | "set_verbose(True)\n", 285 | "\n", 286 | "llm = AzureOpenAI(temperature=0, deployment_name=\"gpt-35-turbo-instruct\", model_name=\"gpt-35-turbo-instruct\", api_version='2023-05-15')\n", 287 | "\n", 288 | "qa = RetrievalQA.from_chain_type(llm=llm, chain_type=\"stuff\", retriever=docsearch.as_retriever())\n", 289 | "\n", 290 | "template = \"\"\"Question: {question}\n", 291 | "\n", 292 | "\"\"\"\n", 293 | "\n", 294 | "prompt = PromptTemplate(template=template, input_variables=[\"question\"])\n", 295 | "\n", 296 | "llm_chain = LLMChain(prompt=prompt, llm=llm)\n", 297 | "\n", 298 | "\n", 299 | "\n", 300 | "\n", 301 | "query = \"Qual o percentual do fundo partidário que deve ser destinado a campanhas eleitorais de negros?\"\n", 302 | "print(llm_chain.run(query))\n", 303 | "\n", 304 | "qa.run(query)" 305 | ] 306 | }, 307 | { 308 | "cell_type": "markdown", 309 | "id": "77a56f6d-8d13-43e9-b301-cda9a45d0e34", 310 | "metadata": { 311 | "nteract": { 312 | "transient": { 313 | "deleting": false 314 | } 315 | } 316 | }, 317 | "source": [ 318 | "### Salvando o arquivo e carregando de novo\n" 319 | ] 320 | }, 321 | { 322 | "cell_type": "code", 323 | "execution_count": 16, 324 | "id": "75d12d53-1bdd-428e-b71e-23d04ca17eda", 325 | "metadata": { 326 | "tags": [] 327 | }, 328 | "outputs": [], 329 | "source": [ 330 | "docsearch.save_local('./data/constituicao/')\n", 331 | "\n", 332 | "\n", 333 | "loaded = FAISS.load_local('./data/constituicao/', embeddings, allow_dangerous_deserialization=True)\n" 334 | ] 335 | } 336 | ], 337 | "metadata": { 338 | "kernelspec": { 339 | "display_name": "Python 3 (ipykernel)", 340 | "language": "python", 341 | "name": "python3" 342 | }, 343 | "language_info": { 344 | "codemirror_mode": { 345 | "name": "ipython", 346 | "version": 3 347 | }, 348 | "file_extension": ".py", 349 | "mimetype": "text/x-python", 350 | "name": "python", 351 | "nbconvert_exporter": "python", 352 | "pygments_lexer": "ipython3", 353 | "version": "3.12.4" 354 | } 355 | }, 356 | "nbformat": 4, 357 | "nbformat_minor": 5 358 | } 359 | -------------------------------------------------------------------------------- /06_functions_classificacao_sentimentos.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "e992deab-e6d6-4478-b58c-464d0dafc71d", 6 | "metadata": {}, 7 | "source": [ 8 | "# Functions\n", 9 | "\n", 10 | "Exemplo de classificação com Functions\n" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": 1, 16 | "id": "b4f5e0eb-d71b-4821-a160-6da1e810377e", 17 | "metadata": { 18 | "tags": [] 19 | }, 20 | "outputs": [], 21 | "source": [ 22 | "import os\n", 23 | "from openai import AzureOpenAI\n", 24 | "from dotenv import load_dotenv\n", 25 | "load_dotenv()\n", 26 | "\n", 27 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 28 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 29 | "\n", 30 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 31 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 32 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 33 | "\n", 34 | "client = AzureOpenAI(\n", 35 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 36 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 37 | " api_key = API_KEY,\n", 38 | ")\n" 39 | ] 40 | }, 41 | { 42 | "cell_type": "code", 43 | "execution_count": 2, 44 | "id": "87ffc308-5fe5-41b5-8a95-3c5b7bdec610", 45 | "metadata": { 46 | "tags": [] 47 | }, 48 | "outputs": [], 49 | "source": [ 50 | "def build_message(role, content):\n", 51 | " return {\"role\":role, \"content\":content}" 52 | ] 53 | }, 54 | { 55 | "cell_type": "code", 56 | "execution_count": 7, 57 | "id": "d62a995e", 58 | "metadata": {}, 59 | "outputs": [], 60 | "source": [ 61 | "tools = [\n", 62 | " {\n", 63 | " \"type\": \"function\",\n", 64 | " \"function\": {\n", 65 | " \"name\": \"reportSentiment\",\n", 66 | " \"description\": \"report the sentiment of the supplied text, and if it have sarcasm in it\",\n", 67 | " \"parameters\": {\n", 68 | " \"type\": \"object\",\n", 69 | " \"properties\": {\n", 70 | " \"sentiment\": {\n", 71 | " \"type\": \"string\",\n", 72 | " \"description\": \"the sentiment of the text (positive, negative, neutral)\",\n", 73 | " },\n", 74 | " \"sarcasm\": {\n", 75 | " \"type\": \"boolean\",\n", 76 | " \"description\": \"if the text has sarcasm\",\n", 77 | " },\n", 78 | "\n", 79 | " },\n", 80 | " \"required\": [\"sentiment\", \"sarcasm\"],\n", 81 | " \"additionalProperties\": False,\n", 82 | " },\n", 83 | " }\n", 84 | " }\n", 85 | "]" 86 | ] 87 | }, 88 | { 89 | "cell_type": "code", 90 | "execution_count": 10, 91 | "id": "2634b014-c3f1-4d25-a26a-7d62ee2c19b3", 92 | "metadata": { 93 | "tags": [] 94 | }, 95 | "outputs": [ 96 | { 97 | "name": "stdout", 98 | "output_type": "stream", 99 | "text": [ 100 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_C1PZrX39cJgfr5m8iIPO9QT4', function=Function(arguments='{\"sentiment\": \"positive\", \"sarcasm\": false}', name='reportSentiment'), type='function')])\n" 101 | ] 102 | } 103 | ], 104 | "source": [ 105 | "\n", 106 | "system_prompt = \"\"\"Você é um assistente para classificar os sentimentos de um texto.\"\"\"\n", 107 | "\n", 108 | "query = \"Estou animado para estréia do Rings of Power amanhã!\"\n", 109 | "\n", 110 | "messages = [ \n", 111 | " build_message(\"system\", system_prompt),\n", 112 | " build_message(\"user\", query),\n", 113 | " \n", 114 | " ]\n", 115 | "\n", 116 | "\n", 117 | "response = client.chat.completions.create(\n", 118 | " model=\"gpt-4o\",\n", 119 | " messages = messages,\n", 120 | " temperature=1,\n", 121 | " max_tokens=400,\n", 122 | " top_p=0.95,\n", 123 | " frequency_penalty=0,\n", 124 | " presence_penalty=0,\n", 125 | " stop=None,\n", 126 | " tools=tools)\n", 127 | "\n", 128 | "response_message = response.choices[0].message\n", 129 | "print(response_message)" 130 | ] 131 | }, 132 | { 133 | "cell_type": "code", 134 | "execution_count": 13, 135 | "id": "bcfed7dc-f31a-4554-bcbd-a68bf22da176", 136 | "metadata": { 137 | "tags": [] 138 | }, 139 | "outputs": [ 140 | { 141 | "name": "stdout", 142 | "output_type": "stream", 143 | "text": [ 144 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_T96YpbHKW8lJPWe1fwcHOu6S', function=Function(arguments='{\"sentiment\": \"negative\", \"sarcasm\": true}', name='reportSentiment'), type='function')])\n" 145 | ] 146 | } 147 | ], 148 | "source": [ 149 | "query = \"Estou animado para estréia do Rings of Power amanhã! SQN!\"\n", 150 | "\n", 151 | "messages = [ \n", 152 | " build_message(\"system\", system_prompt),\n", 153 | " build_message(\"user\", query),\n", 154 | " \n", 155 | " ]\n", 156 | "\n", 157 | "\n", 158 | "response = client.chat.completions.create(\n", 159 | " model=\"gpt-4o\",\n", 160 | " messages = messages,\n", 161 | " temperature=1,\n", 162 | " max_tokens=400,\n", 163 | " top_p=0.95,\n", 164 | " frequency_penalty=0,\n", 165 | " presence_penalty=0,\n", 166 | " stop=None,\n", 167 | " tools=tools)\n", 168 | "\n", 169 | "response_message = response.choices[0].message\n", 170 | "print(response_message)\n" 171 | ] 172 | }, 173 | { 174 | "cell_type": "code", 175 | "execution_count": 14, 176 | "id": "13432bcc-71cd-4fba-a4c8-2f589a254fe4", 177 | "metadata": { 178 | "tags": [] 179 | }, 180 | "outputs": [ 181 | { 182 | "name": "stdout", 183 | "output_type": "stream", 184 | "text": [ 185 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_UjiZEGOLYSZF1cLLeyUEI5IV', function=Function(arguments='{\"sentiment\": \"neutral\", \"sarcasm\": true}', name='reportSentiment'), type='function')])\n" 186 | ] 187 | } 188 | ], 189 | "source": [ 190 | "query = \"O Hotel é tão chique que até as baratas usam gravatas.\"\n", 191 | "\n", 192 | "messages = [ \n", 193 | " build_message(\"system\", system_prompt),\n", 194 | " build_message(\"user\", query),\n", 195 | " \n", 196 | " ]\n", 197 | "\n", 198 | "\n", 199 | "response = client.chat.completions.create(\n", 200 | " model=\"gpt-4o\",\n", 201 | " messages = messages,\n", 202 | " temperature=1,\n", 203 | " max_tokens=400,\n", 204 | " top_p=0.95,\n", 205 | " frequency_penalty=0,\n", 206 | " presence_penalty=0,\n", 207 | " stop=None,\n", 208 | " tools=tools)\n", 209 | "\n", 210 | "response_message = response.choices[0].message\n", 211 | "print(response_message)" 212 | ] 213 | } 214 | ], 215 | "metadata": { 216 | "kernelspec": { 217 | "display_name": "Python 3 (ipykernel)", 218 | "language": "python", 219 | "name": "python3" 220 | }, 221 | "language_info": { 222 | "codemirror_mode": { 223 | "name": "ipython", 224 | "version": 3 225 | }, 226 | "file_extension": ".py", 227 | "mimetype": "text/x-python", 228 | "name": "python", 229 | "nbconvert_exporter": "python", 230 | "pygments_lexer": "ipython3", 231 | "version": "3.12.4" 232 | } 233 | }, 234 | "nbformat": 4, 235 | "nbformat_minor": 5 236 | } 237 | -------------------------------------------------------------------------------- /07_functions_extraction.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "e992deab-e6d6-4478-b58c-464d0dafc71d", 6 | "metadata": {}, 7 | "source": [ 8 | "# Functions\n", 9 | "\n", 10 | "Exemplo de extração de entidades com Functions\n" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": 1, 16 | "id": "b4f5e0eb-d71b-4821-a160-6da1e810377e", 17 | "metadata": { 18 | "tags": [] 19 | }, 20 | "outputs": [], 21 | "source": [ 22 | "import os\n", 23 | "from openai import AzureOpenAI\n", 24 | "from dotenv import load_dotenv\n", 25 | "load_dotenv()\n", 26 | "\n", 27 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 28 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 29 | "\n", 30 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 31 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 32 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 33 | "\n", 34 | "client = AzureOpenAI(\n", 35 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 36 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 37 | " api_key = API_KEY,\n", 38 | ")\n" 39 | ] 40 | }, 41 | { 42 | "cell_type": "code", 43 | "execution_count": 2, 44 | "id": "87ffc308-5fe5-41b5-8a95-3c5b7bdec610", 45 | "metadata": { 46 | "tags": [] 47 | }, 48 | "outputs": [], 49 | "source": [ 50 | "def build_message(role, content):\n", 51 | " return {\"role\":role, \"content\":content}" 52 | ] 53 | }, 54 | { 55 | "cell_type": "code", 56 | "execution_count": 3, 57 | "id": "d62a995e", 58 | "metadata": {}, 59 | "outputs": [], 60 | "source": [ 61 | "tools = [\n", 62 | " {\n", 63 | " \"type\": \"function\",\n", 64 | " \"function\": {\n", 65 | " \"name\": \"contact-information-extraction\",\n", 66 | " \"description\": \"report the contact information extracted from the text\",\n", 67 | " \"parameters\": {\n", 68 | " \"type\": \"object\",\n", 69 | " \"properties\": {\n", 70 | " \"name\": {\n", 71 | " \"type\": \"string\",\n", 72 | " \"description\": \"name extracted from the text\",\n", 73 | " },\n", 74 | " \"email\": {\n", 75 | " \"type\": \"string\",\n", 76 | " \"description\": \"email extracted from the text\",\n", 77 | " },\n", 78 | " \"phone\": {\n", 79 | " \"type\": \"string\",\n", 80 | " \"description\": \"phone extracted from the text\",\n", 81 | " },\n", 82 | " \n", 83 | "\n", 84 | " },\n", 85 | " \"required\": [\"name\"],\n", 86 | " \"additionalProperties\": False,\n", 87 | " },\n", 88 | " }\n", 89 | " }\n", 90 | "]" 91 | ] 92 | }, 93 | { 94 | "cell_type": "code", 95 | "execution_count": 4, 96 | "id": "2634b014-c3f1-4d25-a26a-7d62ee2c19b3", 97 | "metadata": { 98 | "tags": [] 99 | }, 100 | "outputs": [ 101 | { 102 | "name": "stdout", 103 | "output_type": "stream", 104 | "text": [ 105 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_225EvoVwJyCBc1MzAjjyXlHk', function=Function(arguments='{\"name\":\"João\",\"email\":\"joao@contoso.com\"}', name='contact-information-extraction'), type='function')])\n" 106 | ] 107 | } 108 | ], 109 | "source": [ 110 | "\n", 111 | "system_prompt = \"\"\"Você é um assistente para extrair informações de um texto.\"\"\"\n", 112 | "\n", 113 | "query = \"Olá, meu nome é João e meu email é joao@contoso.com\"\n", 114 | "\n", 115 | "messages = [ \n", 116 | " build_message(\"system\", system_prompt),\n", 117 | " build_message(\"user\", query),\n", 118 | " \n", 119 | " ]\n", 120 | "\n", 121 | "\n", 122 | "response = client.chat.completions.create(\n", 123 | " model=\"gpt-4o\",\n", 124 | " messages = messages,\n", 125 | " temperature=1,\n", 126 | " max_tokens=400,\n", 127 | " top_p=0.95,\n", 128 | " frequency_penalty=0,\n", 129 | " presence_penalty=0,\n", 130 | " stop=None,\n", 131 | " tools=tools)\n", 132 | "\n", 133 | "response_message = response.choices[0].message\n", 134 | "print(response_message)" 135 | ] 136 | }, 137 | { 138 | "cell_type": "code", 139 | "execution_count": 5, 140 | "id": "bcfed7dc-f31a-4554-bcbd-a68bf22da176", 141 | "metadata": { 142 | "tags": [] 143 | }, 144 | "outputs": [ 145 | { 146 | "name": "stdout", 147 | "output_type": "stream", 148 | "text": [ 149 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_QOMRQiGmo4Ljg6O1qRsVXoWI', function=Function(arguments='{\"name\":\"Maria\",\"phone\":\"(11) 91234-5678\"}', name='contact-information-extraction'), type='function')])\n" 150 | ] 151 | } 152 | ], 153 | "source": [ 154 | "query = \"Olá, meu nome é Maria e meu telefone é (11) 91234-5678\"\n", 155 | "\n", 156 | "messages = [ \n", 157 | " build_message(\"system\", system_prompt),\n", 158 | " build_message(\"user\", query),\n", 159 | " \n", 160 | " ]\n", 161 | "\n", 162 | "\n", 163 | "response = client.chat.completions.create(\n", 164 | " model=\"gpt-4o\",\n", 165 | " messages = messages,\n", 166 | " temperature=1,\n", 167 | " max_tokens=400,\n", 168 | " top_p=0.95,\n", 169 | " frequency_penalty=0,\n", 170 | " presence_penalty=0,\n", 171 | " stop=None,\n", 172 | " tools=tools)\n", 173 | "\n", 174 | "response_message = response.choices[0].message\n", 175 | "print(response_message)\n" 176 | ] 177 | }, 178 | { 179 | "cell_type": "code", 180 | "execution_count": 6, 181 | "id": "13432bcc-71cd-4fba-a4c8-2f589a254fe4", 182 | "metadata": { 183 | "tags": [] 184 | }, 185 | "outputs": [ 186 | { 187 | "name": "stdout", 188 | "output_type": "stream", 189 | "text": [ 190 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_e0eeE94Zc1uf7XjP8wLSIWoz', function=Function(arguments='{\"name\":\"Maria\",\"email\":\"maria@contoso.com\",\"phone\":\"(11) 91234-5678\"}', name='contact-information-extraction'), type='function')])\n" 191 | ] 192 | } 193 | ], 194 | "source": [ 195 | "query = \"Olá, meu nome é Maria e meu telefone é (11) 91234-5678 e meu e-mail é maria@contoso.com\"\n", 196 | "\n", 197 | "messages = [ \n", 198 | " build_message(\"system\", system_prompt),\n", 199 | " build_message(\"user\", query),\n", 200 | " \n", 201 | " ]\n", 202 | "\n", 203 | "\n", 204 | "response = client.chat.completions.create(\n", 205 | " model=\"gpt-4o\",\n", 206 | " messages = messages,\n", 207 | " temperature=1,\n", 208 | " max_tokens=400,\n", 209 | " top_p=0.95,\n", 210 | " frequency_penalty=0,\n", 211 | " presence_penalty=0,\n", 212 | " stop=None,\n", 213 | " tools=tools)\n", 214 | "\n", 215 | "response_message = response.choices[0].message\n", 216 | "print(response_message)" 217 | ] 218 | }, 219 | { 220 | "cell_type": "code", 221 | "execution_count": 7, 222 | "id": "b2bdb0ff", 223 | "metadata": {}, 224 | "outputs": [ 225 | { 226 | "name": "stdout", 227 | "output_type": "stream", 228 | "text": [ 229 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_I2KzIqCEAi5D7VUSRBELD9LC', function=Function(arguments='{\"name\": \"Maria\", \"email\": \"maria@contoso.com\", \"phone\": \"(11) 91234-5678\"}', name='contact-information-extraction'), type='function'), ChatCompletionMessageToolCall(id='call_JmMHiUNRtWFDoReBdmSgxmbO', function=Function(arguments='{\"name\": \"João\", \"email\": \"joao@contoso.com\", \"phone\": \"(11) 91234-5678\"}', name='contact-information-extraction'), type='function')])\n" 230 | ] 231 | } 232 | ], 233 | "source": [ 234 | "query = \"Maria - telefone é (11) 91234-5678 - e-mail é maria@contoso.com. \\n João - telefone é (11) 91234-5678 - e-mail é joao@contoso.com\"\n", 235 | "\n", 236 | "messages = [ \n", 237 | " build_message(\"system\", system_prompt),\n", 238 | " build_message(\"user\", query),\n", 239 | " \n", 240 | " ]\n", 241 | "\n", 242 | "\n", 243 | "response = client.chat.completions.create(\n", 244 | " model=\"gpt-4o\",\n", 245 | " messages = messages,\n", 246 | " temperature=1,\n", 247 | " max_tokens=400,\n", 248 | " top_p=0.95,\n", 249 | " frequency_penalty=0,\n", 250 | " presence_penalty=0,\n", 251 | " stop=None,\n", 252 | " tools=tools)\n", 253 | "\n", 254 | "response_message = response.choices[0].message\n", 255 | "print(response_message)" 256 | ] 257 | } 258 | ], 259 | "metadata": { 260 | "kernelspec": { 261 | "display_name": "Python 3 (ipykernel)", 262 | "language": "python", 263 | "name": "python3" 264 | }, 265 | "language_info": { 266 | "codemirror_mode": { 267 | "name": "ipython", 268 | "version": 3 269 | }, 270 | "file_extension": ".py", 271 | "mimetype": "text/x-python", 272 | "name": "python", 273 | "nbconvert_exporter": "python", 274 | "pygments_lexer": "ipython3", 275 | "version": "3.12.4" 276 | } 277 | }, 278 | "nbformat": 4, 279 | "nbformat_minor": 5 280 | } 281 | -------------------------------------------------------------------------------- /07_functions_reservation.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "e992deab-e6d6-4478-b58c-464d0dafc71d", 6 | "metadata": {}, 7 | "source": [ 8 | "# Functions\n", 9 | "\n", 10 | "Exemplo de reserva de restaurantes com functions\n" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": 1, 16 | "id": "b4f5e0eb-d71b-4821-a160-6da1e810377e", 17 | "metadata": { 18 | "tags": [] 19 | }, 20 | "outputs": [], 21 | "source": [ 22 | "import os\n", 23 | "from openai import AzureOpenAI\n", 24 | "from dotenv import load_dotenv\n", 25 | "load_dotenv()\n", 26 | "\n", 27 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 28 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 29 | "\n", 30 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 31 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 32 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 33 | "\n", 34 | "client = AzureOpenAI(\n", 35 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 36 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 37 | " api_key = API_KEY,\n", 38 | ")\n" 39 | ] 40 | }, 41 | { 42 | "cell_type": "code", 43 | "execution_count": 2, 44 | "id": "87ffc308-5fe5-41b5-8a95-3c5b7bdec610", 45 | "metadata": { 46 | "tags": [] 47 | }, 48 | "outputs": [], 49 | "source": [ 50 | "def build_message(role, content):\n", 51 | " return {\"role\":role, \"content\":content}" 52 | ] 53 | }, 54 | { 55 | "cell_type": "code", 56 | "execution_count": 3, 57 | "id": "d62a995e", 58 | "metadata": {}, 59 | "outputs": [], 60 | "source": [ 61 | "tools = [\n", 62 | " {\n", 63 | " \"type\": \"function\",\n", 64 | " \"function\": {\n", 65 | " \"name\": \"bookRestaurant\",\n", 66 | " \"description\": \"Book a restaurant\",\n", 67 | " \"parameters\": {\n", 68 | " \"type\": \"object\",\n", 69 | " \"properties\": {\n", 70 | " \"name\": {\n", 71 | " \"type\": \"string\",\n", 72 | " \"description\": \"name of the restaurant\",\n", 73 | " },\n", 74 | " \"persons\": {\n", 75 | " \"type\": \"integer\",\n", 76 | " \"description\": \"quantity of persons for the reservation\",\n", 77 | " },\n", 78 | " \"date\": {\n", 79 | " \"type\": \"string\",\n", 80 | " \"description\": \"date for the reservation\",\n", 81 | " },\n", 82 | " \"time\": {\n", 83 | " \"type\": \"string\",\n", 84 | " \"description\": \"time for the reservation\",\n", 85 | " }\n", 86 | " \n", 87 | "\n", 88 | " },\n", 89 | " \"required\": [\"name\", \"persons\", \"date\", \"time\"],\n", 90 | " \"additionalProperties\": False,\n", 91 | " },\n", 92 | " }\n", 93 | " }\n", 94 | "]" 95 | ] 96 | }, 97 | { 98 | "cell_type": "code", 99 | "execution_count": 15, 100 | "id": "2634b014-c3f1-4d25-a26a-7d62ee2c19b3", 101 | "metadata": { 102 | "tags": [] 103 | }, 104 | "outputs": [ 105 | { 106 | "name": "stdout", 107 | "output_type": "stream", 108 | "text": [ 109 | "ChatCompletionMessage(content='Olá! Como posso ajudar você hoje? Está procurando um restaurante ou gostaria de fazer uma reserva?', refusal=None, role='assistant', function_call=None, tool_calls=None)\n" 110 | ] 111 | } 112 | ], 113 | "source": [ 114 | "\n", 115 | "system_prompt = \"\"\"Você é um assistente virtual que ajuda as pessoas a encontrar um restaurante e fazer uma reserva. Data atual: 2024-09-04.\"\"\"\n", 116 | "\n", 117 | "query = \"Olá\"\n", 118 | "\n", 119 | "messages = [ \n", 120 | " build_message(\"system\", system_prompt),\n", 121 | " build_message(\"user\", query),\n", 122 | " \n", 123 | " ]\n", 124 | "\n", 125 | "\n", 126 | "response = client.chat.completions.create(\n", 127 | " model=\"gpt-4o\",\n", 128 | " messages = messages,\n", 129 | " temperature=1,\n", 130 | " max_tokens=400,\n", 131 | " top_p=0.95,\n", 132 | " frequency_penalty=0,\n", 133 | " presence_penalty=0,\n", 134 | " stop=None,\n", 135 | " tools=tools)\n", 136 | "\n", 137 | "response_message = response.choices[0].message\n", 138 | "print(response_message)\n", 139 | "\n", 140 | "messages.append(build_message(\"assistant\", response_message.content))" 141 | ] 142 | }, 143 | { 144 | "cell_type": "code", 145 | "execution_count": 16, 146 | "id": "bcfed7dc-f31a-4554-bcbd-a68bf22da176", 147 | "metadata": { 148 | "tags": [] 149 | }, 150 | "outputs": [ 151 | { 152 | "name": "stdout", 153 | "output_type": "stream", 154 | "text": [ 155 | "ChatCompletionMessage(content='Ótimo! Aqui estão alguns restaurantes mexicanos em São Paulo que você pode gostar:\\n\\n1. **Mé Taco**\\n - Endereço: R. Augusta, 430 - Consolação, São Paulo - SP\\n - Descrição: Conhecido por seus tacos autênticos e atmosfera descontraída.\\n\\n2. **La Mexicana**\\n - Endereço: Av. São Luís, 86 - República, São Paulo - SP\\n - Descrição: Um lugar tradicional com pratos típicos mexicanos.\\n\\n3. **Yucatán**\\n - Endereço: R. dos Três Irmãos, 158 - Vila Progredior, São Paulo - SP\\n - Descrição: Restaurante com ambiente acolhedor e diversas opções de pratos mexicanos.\\n\\nVocê gostaria de mais informações sobre algum desses restaurantes ou deseja fazer uma reserva?', refusal=None, role='assistant', function_call=None, tool_calls=None)\n" 156 | ] 157 | } 158 | ], 159 | "source": [ 160 | "messages.append(build_message(\"user\", \"Quero um restaurante mexicano em São Paulo\"))\n", 161 | "\n", 162 | "\n", 163 | "response = client.chat.completions.create(\n", 164 | " model=\"gpt-4o\",\n", 165 | " messages = messages,\n", 166 | " temperature=1,\n", 167 | " max_tokens=400,\n", 168 | " top_p=0.95,\n", 169 | " frequency_penalty=0,\n", 170 | " presence_penalty=0,\n", 171 | " stop=None,\n", 172 | " tools=tools)\n", 173 | "\n", 174 | "response_message = response.choices[0].message\n", 175 | "print(response_message)\n", 176 | "\n", 177 | "messages.append(build_message(\"assistant\", response_message.content))\n" 178 | ] 179 | }, 180 | { 181 | "cell_type": "code", 182 | "execution_count": 17, 183 | "id": "13432bcc-71cd-4fba-a4c8-2f589a254fe4", 184 | "metadata": { 185 | "tags": [] 186 | }, 187 | "outputs": [ 188 | { 189 | "name": "stdout", 190 | "output_type": "stream", 191 | "text": [ 192 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_CfgRPqIpSYECYaOxR9KidGri', function=Function(arguments='{\"name\":\"Hecho em México\",\"persons\":2,\"date\":\"2024-09-10\",\"time\":\"19:00\"}', name='bookRestaurant'), type='function')])\n" 193 | ] 194 | } 195 | ], 196 | "source": [ 197 | "\n", 198 | "messages.append(build_message(\"user\", \"Quero fazer uma reserva para 2 pessoas no Hecho em México no dia 10 de setembro às 19h\"))\n", 199 | "\n", 200 | "\n", 201 | "response = client.chat.completions.create(\n", 202 | " model=\"gpt-4o\",\n", 203 | " messages = messages,\n", 204 | " temperature=1,\n", 205 | " max_tokens=400,\n", 206 | " top_p=0.95,\n", 207 | " frequency_penalty=0,\n", 208 | " presence_penalty=0,\n", 209 | " stop=None,\n", 210 | " tools=tools)\n", 211 | "\n", 212 | "response_message = response.choices[0].message\n", 213 | "print(response_message)\n", 214 | "\n", 215 | "messages.append(response_message)" 216 | ] 217 | }, 218 | { 219 | "cell_type": "code", 220 | "execution_count": 18, 221 | "id": "b2bdb0ff", 222 | "metadata": {}, 223 | "outputs": [ 224 | { 225 | "name": "stdout", 226 | "output_type": "stream", 227 | "text": [ 228 | "ChatCompletionMessage(content='Sua reserva para 2 pessoas no restaurante \"Hecho em México\" no dia 10 de setembro às 19h foi confirmada. \\n\\nSe precisar de mais alguma coisa, é só me avisar! Aproveite sua refeição!', refusal=None, role='assistant', function_call=None, tool_calls=None)\n" 229 | ] 230 | } 231 | ], 232 | "source": [ 233 | "\n", 234 | "messages.append(build_message(\"tool\", \"'OK'\"))\n", 235 | "messages[-1][\"tool_call_id\"] = messages[-2].tool_calls[0].id\t\n", 236 | "\n", 237 | "response = client.chat.completions.create(\n", 238 | " model=\"gpt-4o\",\n", 239 | " messages = messages,\n", 240 | " temperature=1,\n", 241 | " max_tokens=400,\n", 242 | " top_p=0.95,\n", 243 | " frequency_penalty=0,\n", 244 | " presence_penalty=0,\n", 245 | " stop=None,\n", 246 | " tools=tools)\n", 247 | "\n", 248 | "response_message = response.choices[0].message\n", 249 | "print(response_message)\n", 250 | "\n", 251 | "messages.append(build_message(\"assistant\", response_message.content))" 252 | ] 253 | }, 254 | { 255 | "cell_type": "code", 256 | "execution_count": 19, 257 | "id": "d788b173", 258 | "metadata": {}, 259 | "outputs": [ 260 | { 261 | "data": { 262 | "text/plain": [ 263 | "[{'role': 'system',\n", 264 | " 'content': 'Você é um assistente virtual que ajuda as pessoas a encontrar um restaurante e fazer uma reserva. Data atual: 2024-09-04.'},\n", 265 | " {'role': 'user', 'content': 'Olá'},\n", 266 | " {'role': 'assistant',\n", 267 | " 'content': 'Olá! Como posso ajudar você hoje? Está procurando um restaurante ou gostaria de fazer uma reserva?'},\n", 268 | " {'role': 'user', 'content': 'Quero um restaurante mexicano em São Paulo'},\n", 269 | " {'role': 'assistant',\n", 270 | " 'content': 'Ótimo! Aqui estão alguns restaurantes mexicanos em São Paulo que você pode gostar:\\n\\n1. **Mé Taco**\\n - Endereço: R. Augusta, 430 - Consolação, São Paulo - SP\\n - Descrição: Conhecido por seus tacos autênticos e atmosfera descontraída.\\n\\n2. **La Mexicana**\\n - Endereço: Av. São Luís, 86 - República, São Paulo - SP\\n - Descrição: Um lugar tradicional com pratos típicos mexicanos.\\n\\n3. **Yucatán**\\n - Endereço: R. dos Três Irmãos, 158 - Vila Progredior, São Paulo - SP\\n - Descrição: Restaurante com ambiente acolhedor e diversas opções de pratos mexicanos.\\n\\nVocê gostaria de mais informações sobre algum desses restaurantes ou deseja fazer uma reserva?'},\n", 271 | " {'role': 'user',\n", 272 | " 'content': 'Quero fazer uma reserva para 2 pessoas no Hecho em México no dia 10 de setembro às 19h'},\n", 273 | " ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_CfgRPqIpSYECYaOxR9KidGri', function=Function(arguments='{\"name\":\"Hecho em México\",\"persons\":2,\"date\":\"2024-09-10\",\"time\":\"19:00\"}', name='bookRestaurant'), type='function')]),\n", 274 | " {'role': 'tool',\n", 275 | " 'content': \"'OK'\",\n", 276 | " 'tool_call_id': 'call_CfgRPqIpSYECYaOxR9KidGri'},\n", 277 | " {'role': 'assistant',\n", 278 | " 'content': 'Sua reserva para 2 pessoas no restaurante \"Hecho em México\" no dia 10 de setembro às 19h foi confirmada. \\n\\nSe precisar de mais alguma coisa, é só me avisar! Aproveite sua refeição!'}]" 279 | ] 280 | }, 281 | "execution_count": 19, 282 | "metadata": {}, 283 | "output_type": "execute_result" 284 | } 285 | ], 286 | "source": [ 287 | "messages" 288 | ] 289 | } 290 | ], 291 | "metadata": { 292 | "kernelspec": { 293 | "display_name": "Python 3 (ipykernel)", 294 | "language": "python", 295 | "name": "python3" 296 | }, 297 | "language_info": { 298 | "codemirror_mode": { 299 | "name": "ipython", 300 | "version": 3 301 | }, 302 | "file_extension": ".py", 303 | "mimetype": "text/x-python", 304 | "name": "python", 305 | "nbconvert_exporter": "python", 306 | "pygments_lexer": "ipython3", 307 | "version": "3.12.4" 308 | } 309 | }, 310 | "nbformat": 4, 311 | "nbformat_minor": 5 312 | } 313 | -------------------------------------------------------------------------------- /08_functions_banco.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "e992deab-e6d6-4478-b58c-464d0dafc71d", 6 | "metadata": {}, 7 | "source": [ 8 | "# Functions\n", 9 | "\n", 10 | "Exemplo de chatbot para banco com Functions" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": 12, 16 | "id": "b4f5e0eb-d71b-4821-a160-6da1e810377e", 17 | "metadata": { 18 | "tags": [] 19 | }, 20 | "outputs": [], 21 | "source": [ 22 | "import os\n", 23 | "from openai import AzureOpenAI\n", 24 | "from dotenv import load_dotenv\n", 25 | "load_dotenv()\n", 26 | "\n", 27 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 28 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 29 | "\n", 30 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 31 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 32 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 33 | "\n", 34 | "client = AzureOpenAI(\n", 35 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 36 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 37 | " api_key = API_KEY,\n", 38 | ")\n" 39 | ] 40 | }, 41 | { 42 | "cell_type": "code", 43 | "execution_count": 13, 44 | "id": "87ffc308-5fe5-41b5-8a95-3c5b7bdec610", 45 | "metadata": { 46 | "tags": [] 47 | }, 48 | "outputs": [], 49 | "source": [ 50 | "def build_message(role, content):\n", 51 | " return {\"role\":role, \"content\":content}" 52 | ] 53 | }, 54 | { 55 | "cell_type": "code", 56 | "execution_count": 14, 57 | "id": "d62a995e", 58 | "metadata": {}, 59 | "outputs": [], 60 | "source": [ 61 | "from bankdomain import BankFunctions, Boleto, ContaCorrente\n", 62 | "\n", 63 | "functions = BankFunctions(ContaCorrente(numero=\"123\", saldo=1000, apelido=\"conta principal\"),[\n", 64 | " Boleto(100, \"123\", \"Escola\"),\n", 65 | " Boleto(200, \"456\", \"Escola\"),\n", 66 | " Boleto(1200, \"789\", \"Escola\"),\n", 67 | " ],\n", 68 | " [\n", 69 | " ContaCorrente(numero=\"987\", saldo=0, apelido=\"André\"),\n", 70 | " ContaCorrente(numero=\"654\", saldo=0, apelido=\"João\"),\n", 71 | " ])\n", 72 | "\n", 73 | "tools = []\n", 74 | "for function in functions.get_functions():\n", 75 | " tools.append({\"type\": \"function\", \"function\": function})\n", 76 | "\n" 77 | ] 78 | }, 79 | { 80 | "cell_type": "code", 81 | "execution_count": 15, 82 | "id": "2634b014-c3f1-4d25-a26a-7d62ee2c19b3", 83 | "metadata": { 84 | "tags": [] 85 | }, 86 | "outputs": [ 87 | { 88 | "name": "stdout", 89 | "output_type": "stream", 90 | "text": [ 91 | "ChatCompletionMessage(content='Olá! Como posso ajudar você hoje?', refusal=None, role='assistant', function_call=None, tool_calls=None)\n" 92 | ] 93 | } 94 | ], 95 | "source": [ 96 | "system_prompt = \"\"\"\"Voce é um assistente bancário que ajuda um cliente a transacionar em usa conta. Seja solicito e educado.\", \"Este é uma simulação de um assistente bancário, que simula um bot de operações bancárias com linguagem natural.\\nSe tiver dúvidas das capacidades, pergunte o que ele pode fazer.\" Data atual: 2024-09-04.\"\"\"\n", 97 | "\n", 98 | "query = \"Olá\"\n", 99 | "\n", 100 | "messages = [ \n", 101 | " build_message(\"system\", system_prompt),\n", 102 | " build_message(\"user\", query),\n", 103 | " \n", 104 | " ]\n", 105 | "\n", 106 | "\n", 107 | "response = client.chat.completions.create(\n", 108 | " model=\"gpt-4o\",\n", 109 | " messages = messages,\n", 110 | " temperature=1,\n", 111 | " max_tokens=400,\n", 112 | " top_p=0.95,\n", 113 | " frequency_penalty=0,\n", 114 | " presence_penalty=0,\n", 115 | " stop=None,\n", 116 | " tools=tools)\n", 117 | "\n", 118 | "response_message = response.choices[0].message\n", 119 | "print(response_message)\n", 120 | "\n", 121 | "messages.append(build_message(\"assistant\", response_message.content))" 122 | ] 123 | }, 124 | { 125 | "cell_type": "code", 126 | "execution_count": 16, 127 | "id": "59cd593f", 128 | "metadata": {}, 129 | "outputs": [], 130 | "source": [ 131 | "import json\n", 132 | "\n", 133 | "def todict(obj):\n", 134 | " tool_calls = None\n", 135 | " if (obj.tool_calls is not None):\n", 136 | " tool_calls = []\n", 137 | " for tool_call in obj.tool_calls:\n", 138 | " tool_calls.append({\"id\": tool_call.id, \"function\": {\"name\": tool_call.function.name, \"arguments\": tool_call.function.arguments}, \"type\": tool_call.type})\n", 139 | " return {\"content\": obj.content, \"role\": obj.role, \"tool_calls\": tool_calls}\n", 140 | "\n", 141 | "def function_call(functionsObject, messages):\n", 142 | " try:\n", 143 | " print('function_call')\n", 144 | " #for message in chat_context[\"conversation\"]:\n", 145 | " # print(message[\"role\"])\n", 146 | " # print(message[\"content\"])\n", 147 | " \n", 148 | " response_message = client.chat.completions.create(\n", 149 | " model=\"gpt-4o\",\n", 150 | " messages=messages,\n", 151 | " tools=tools,\n", 152 | " tool_choice=\"auto\", \n", 153 | " ).choices[0].message\n", 154 | " print(response_message)\n", 155 | " if response_message.tool_calls is not None:\n", 156 | " messages.append( # adding assistant response to messages\n", 157 | " todict(response_message)\n", 158 | " )\n", 159 | " for tool_call in response_message.tool_calls:\n", 160 | " # Call the function. The JSON response may not always be valid so make sure to handle errors\n", 161 | " function_name = tool_call.function.name\n", 162 | " function_args = json.loads(tool_call.function.arguments)\n", 163 | " function_response = getattr(functionsObject, function_name)(**function_args)\n", 164 | " messages.append( # adding function response to messages\n", 165 | " {\n", 166 | " \"tool_call_id\": tool_call.id,\n", 167 | " \"role\": \"tool\",\n", 168 | " \"name\": function_name,\n", 169 | " \"content\": json.dumps(function_response),\n", 170 | " }\n", 171 | " ) \n", 172 | " return function_call(functionsObject, messages)\n", 173 | " else:\n", 174 | " print(\"not function\")\n", 175 | " messages.append( # adding assistant response to messages\n", 176 | " {\n", 177 | " \"role\": response_message.role,\n", 178 | " \"content\": response_message.content,\n", 179 | " }\n", 180 | " )\n", 181 | " print(messages)\n", 182 | " return \n", 183 | " except Exception as e:\n", 184 | " print(e)\n", 185 | " return" 186 | ] 187 | }, 188 | { 189 | "cell_type": "code", 190 | "execution_count": 17, 191 | "id": "bcfed7dc-f31a-4554-bcbd-a68bf22da176", 192 | "metadata": { 193 | "tags": [] 194 | }, 195 | "outputs": [ 196 | { 197 | "name": "stdout", 198 | "output_type": "stream", 199 | "text": [ 200 | "function_call\n", 201 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_79Y4bXaN1Ir5pjVwdwpABwqd', function=Function(arguments='{}', name='saldo'), type='function')])\n", 202 | "function_call\n", 203 | "ChatCompletionMessage(content='O saldo da sua conta é R$ 1.000,00. Há algo mais que eu possa ajudar?', refusal=None, role='assistant', function_call=None, tool_calls=None)\n", 204 | "not function\n", 205 | "[{'role': 'system', 'content': '\"Voce é um assistente bancário que ajuda um cliente a transacionar em usa conta. Seja solicito e educado.\", \"Este é uma simulação de um assistente bancário, que simula um bot de operações bancárias com linguagem natural.\\nSe tiver dúvidas das capacidades, pergunte o que ele pode fazer.\" Data atual: 2024-09-04.'}, {'role': 'user', 'content': 'Olá'}, {'role': 'assistant', 'content': 'Olá! Como posso ajudar você hoje?'}, {'role': 'user', 'content': 'Qual é o saldo da minha conta?'}, {'content': None, 'role': 'assistant', 'tool_calls': [{'id': 'call_79Y4bXaN1Ir5pjVwdwpABwqd', 'function': {'name': 'saldo', 'arguments': '{}'}, 'type': 'function'}]}, {'tool_call_id': 'call_79Y4bXaN1Ir5pjVwdwpABwqd', 'role': 'tool', 'name': 'saldo', 'content': '1000'}, {'role': 'assistant', 'content': 'O saldo da sua conta é R$ 1.000,00. Há algo mais que eu possa ajudar?'}]\n" 206 | ] 207 | }, 208 | { 209 | "data": { 210 | "text/plain": [ 211 | "[{'role': 'system',\n", 212 | " 'content': '\"Voce é um assistente bancário que ajuda um cliente a transacionar em usa conta. Seja solicito e educado.\", \"Este é uma simulação de um assistente bancário, que simula um bot de operações bancárias com linguagem natural.\\nSe tiver dúvidas das capacidades, pergunte o que ele pode fazer.\" Data atual: 2024-09-04.'},\n", 213 | " {'role': 'user', 'content': 'Olá'},\n", 214 | " {'role': 'assistant', 'content': 'Olá! Como posso ajudar você hoje?'},\n", 215 | " {'role': 'user', 'content': 'Qual é o saldo da minha conta?'},\n", 216 | " {'content': None,\n", 217 | " 'role': 'assistant',\n", 218 | " 'tool_calls': [{'id': 'call_79Y4bXaN1Ir5pjVwdwpABwqd',\n", 219 | " 'function': {'name': 'saldo', 'arguments': '{}'},\n", 220 | " 'type': 'function'}]},\n", 221 | " {'tool_call_id': 'call_79Y4bXaN1Ir5pjVwdwpABwqd',\n", 222 | " 'role': 'tool',\n", 223 | " 'name': 'saldo',\n", 224 | " 'content': '1000'},\n", 225 | " {'role': 'assistant',\n", 226 | " 'content': 'O saldo da sua conta é R$ 1.000,00. Há algo mais que eu possa ajudar?'}]" 227 | ] 228 | }, 229 | "execution_count": 17, 230 | "metadata": {}, 231 | "output_type": "execute_result" 232 | } 233 | ], 234 | "source": [ 235 | "messages.append(build_message(\"user\", \"Qual é o saldo da minha conta?\"))\n", 236 | "\n", 237 | "function_call(functions, messages)\n", 238 | "\n", 239 | "messages" 240 | ] 241 | }, 242 | { 243 | "cell_type": "code", 244 | "execution_count": 18, 245 | "id": "13432bcc-71cd-4fba-a4c8-2f589a254fe4", 246 | "metadata": { 247 | "tags": [] 248 | }, 249 | "outputs": [ 250 | { 251 | "name": "stdout", 252 | "output_type": "stream", 253 | "text": [ 254 | "function_call\n", 255 | "ChatCompletionMessage(content='Vou começar verificando os boletos pendentes. Em seguida, farei os pagamentos possíveis e a transferência solicitada. Um momento, por favor.', refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_BG4g80PJo74eJf7zwpMSXqJF', function=Function(arguments='{}', name='boletos_pendentes'), type='function')])\n", 256 | "function_call\n", 257 | "ChatCompletionMessage(content='Aqui estão os boletos pendentes encontrados:\\n\\n1. Boleto número 123 - Valor: R$ 100,00\\n2. Boleto número 456 - Valor: R$ 200,00\\n3. Boleto número 789 - Valor: R$ 1200,00\\n\\nLevando em consideração que o saldo atual é de R$ 1.000,00, vou prosseguir com o pagamento dos boletos que estão dentro deste limite e em seguida farei a transferência de R$ 200,00 para a conta do João. \\n\\nVou começar pagando os boletos de R$ 100,00 e R$ 200,00.', refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_ZC7tV5hXLGChfpu7HvR9O63B', function=Function(arguments='{\"numero_boleto\": \"123\"}', name='pagarBoleto'), type='function'), ChatCompletionMessageToolCall(id='call_Xhh8rEfNnMZ6pNVD0GbZGFad', function=Function(arguments='{\"numero_boleto\": \"456\"}', name='pagarBoleto'), type='function')])\n", 258 | "function_call\n", 259 | "ChatCompletionMessage(content='Os boletos de R$ 100,00 e R$ 200,00 foram pagos com sucesso. \\n\\nAgora, vou prosseguir com a transferência de R$ 200,00 para a conta do João. Primeiro, vou obter o número da conta dele pelo apelido \"João\".', refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_II57ZaH5XTG3pWMdtdacCFqe', function=Function(arguments='{\"apelido\":\"João\"}', name='obter_numero_conta_por_apelido'), type='function')])\n", 260 | "function_call\n", 261 | "ChatCompletionMessage(content=None, refusal=None, role='assistant', function_call=None, tool_calls=[ChatCompletionMessageToolCall(id='call_n4C6BytEbVRZixZiamdJZntd', function=Function(arguments='{\"valor\":200,\"numero_conta_destino\":\"654\"}', name='transferir'), type='function')])\n", 262 | "function_call\n", 263 | "ChatCompletionMessage(content='Todos os procedimentos foram realizados com sucesso:\\n\\n- Os boletos de R$ 100,00 e R$ 200,00 foram pagos.\\n- A transferência de R$ 200,00 para a conta do João foi realizada com sucesso.\\n\\nPosso ajudar com mais alguma coisa?', refusal=None, role='assistant', function_call=None, tool_calls=None)\n", 264 | "not function\n", 265 | "[{'role': 'system', 'content': '\"Voce é um assistente bancário que ajuda um cliente a transacionar em usa conta. Seja solicito e educado.\", \"Este é uma simulação de um assistente bancário, que simula um bot de operações bancárias com linguagem natural.\\nSe tiver dúvidas das capacidades, pergunte o que ele pode fazer.\" Data atual: 2024-09-04.'}, {'role': 'user', 'content': 'Olá'}, {'role': 'assistant', 'content': 'Olá! Como posso ajudar você hoje?'}, {'role': 'user', 'content': 'Qual é o saldo da minha conta?'}, {'content': None, 'role': 'assistant', 'tool_calls': [{'id': 'call_79Y4bXaN1Ir5pjVwdwpABwqd', 'function': {'name': 'saldo', 'arguments': '{}'}, 'type': 'function'}]}, {'tool_call_id': 'call_79Y4bXaN1Ir5pjVwdwpABwqd', 'role': 'tool', 'name': 'saldo', 'content': '1000'}, {'role': 'assistant', 'content': 'O saldo da sua conta é R$ 1.000,00. Há algo mais que eu possa ajudar?'}, {'role': 'user', 'content': 'Pague todos os boletos pendentes que não estouram o saldo e depois transfira 200 reais para a conta do João.'}, {'content': 'Vou começar verificando os boletos pendentes. Em seguida, farei os pagamentos possíveis e a transferência solicitada. Um momento, por favor.', 'role': 'assistant', 'tool_calls': [{'id': 'call_BG4g80PJo74eJf7zwpMSXqJF', 'function': {'name': 'boletos_pendentes', 'arguments': '{}'}, 'type': 'function'}]}, {'tool_call_id': 'call_BG4g80PJo74eJf7zwpMSXqJF', 'role': 'tool', 'name': 'boletos_pendentes', 'content': '\"Boleto Pendentes:\\\\nNumero: 123 - Valor: 100\\\\nNumero: 456 - Valor: 200\\\\nNumero: 789 - Valor: 1200\"'}, {'content': 'Aqui estão os boletos pendentes encontrados:\\n\\n1. Boleto número 123 - Valor: R$ 100,00\\n2. Boleto número 456 - Valor: R$ 200,00\\n3. Boleto número 789 - Valor: R$ 1200,00\\n\\nLevando em consideração que o saldo atual é de R$ 1.000,00, vou prosseguir com o pagamento dos boletos que estão dentro deste limite e em seguida farei a transferência de R$ 200,00 para a conta do João. \\n\\nVou começar pagando os boletos de R$ 100,00 e R$ 200,00.', 'role': 'assistant', 'tool_calls': [{'id': 'call_ZC7tV5hXLGChfpu7HvR9O63B', 'function': {'name': 'pagarBoleto', 'arguments': '{\"numero_boleto\": \"123\"}'}, 'type': 'function'}, {'id': 'call_Xhh8rEfNnMZ6pNVD0GbZGFad', 'function': {'name': 'pagarBoleto', 'arguments': '{\"numero_boleto\": \"456\"}'}, 'type': 'function'}]}, {'tool_call_id': 'call_ZC7tV5hXLGChfpu7HvR9O63B', 'role': 'tool', 'name': 'pagarBoleto', 'content': '\"Boleto pago com sucesso\"'}, {'tool_call_id': 'call_Xhh8rEfNnMZ6pNVD0GbZGFad', 'role': 'tool', 'name': 'pagarBoleto', 'content': '\"Boleto pago com sucesso\"'}, {'content': 'Os boletos de R$ 100,00 e R$ 200,00 foram pagos com sucesso. \\n\\nAgora, vou prosseguir com a transferência de R$ 200,00 para a conta do João. Primeiro, vou obter o número da conta dele pelo apelido \"João\".', 'role': 'assistant', 'tool_calls': [{'id': 'call_II57ZaH5XTG3pWMdtdacCFqe', 'function': {'name': 'obter_numero_conta_por_apelido', 'arguments': '{\"apelido\":\"João\"}'}, 'type': 'function'}]}, {'tool_call_id': 'call_II57ZaH5XTG3pWMdtdacCFqe', 'role': 'tool', 'name': 'obter_numero_conta_por_apelido', 'content': '\"654\"'}, {'content': None, 'role': 'assistant', 'tool_calls': [{'id': 'call_n4C6BytEbVRZixZiamdJZntd', 'function': {'name': 'transferir', 'arguments': '{\"valor\":200,\"numero_conta_destino\":\"654\"}'}, 'type': 'function'}]}, {'tool_call_id': 'call_n4C6BytEbVRZixZiamdJZntd', 'role': 'tool', 'name': 'transferir', 'content': '\"Transfer\\\\u00eancia realizada com sucesso\"'}, {'role': 'assistant', 'content': 'Todos os procedimentos foram realizados com sucesso:\\n\\n- Os boletos de R$ 100,00 e R$ 200,00 foram pagos.\\n- A transferência de R$ 200,00 para a conta do João foi realizada com sucesso.\\n\\nPosso ajudar com mais alguma coisa?'}]\n" 266 | ] 267 | }, 268 | { 269 | "data": { 270 | "text/plain": [ 271 | "[{'role': 'system',\n", 272 | " 'content': '\"Voce é um assistente bancário que ajuda um cliente a transacionar em usa conta. Seja solicito e educado.\", \"Este é uma simulação de um assistente bancário, que simula um bot de operações bancárias com linguagem natural.\\nSe tiver dúvidas das capacidades, pergunte o que ele pode fazer.\" Data atual: 2024-09-04.'},\n", 273 | " {'role': 'user', 'content': 'Olá'},\n", 274 | " {'role': 'assistant', 'content': 'Olá! Como posso ajudar você hoje?'},\n", 275 | " {'role': 'user', 'content': 'Qual é o saldo da minha conta?'},\n", 276 | " {'content': None,\n", 277 | " 'role': 'assistant',\n", 278 | " 'tool_calls': [{'id': 'call_79Y4bXaN1Ir5pjVwdwpABwqd',\n", 279 | " 'function': {'name': 'saldo', 'arguments': '{}'},\n", 280 | " 'type': 'function'}]},\n", 281 | " {'tool_call_id': 'call_79Y4bXaN1Ir5pjVwdwpABwqd',\n", 282 | " 'role': 'tool',\n", 283 | " 'name': 'saldo',\n", 284 | " 'content': '1000'},\n", 285 | " {'role': 'assistant',\n", 286 | " 'content': 'O saldo da sua conta é R$ 1.000,00. Há algo mais que eu possa ajudar?'},\n", 287 | " {'role': 'user',\n", 288 | " 'content': 'Pague todos os boletos pendentes que não estouram o saldo e depois transfira 200 reais para a conta do João.'},\n", 289 | " {'content': 'Vou começar verificando os boletos pendentes. Em seguida, farei os pagamentos possíveis e a transferência solicitada. Um momento, por favor.',\n", 290 | " 'role': 'assistant',\n", 291 | " 'tool_calls': [{'id': 'call_BG4g80PJo74eJf7zwpMSXqJF',\n", 292 | " 'function': {'name': 'boletos_pendentes', 'arguments': '{}'},\n", 293 | " 'type': 'function'}]},\n", 294 | " {'tool_call_id': 'call_BG4g80PJo74eJf7zwpMSXqJF',\n", 295 | " 'role': 'tool',\n", 296 | " 'name': 'boletos_pendentes',\n", 297 | " 'content': '\"Boleto Pendentes:\\\\nNumero: 123 - Valor: 100\\\\nNumero: 456 - Valor: 200\\\\nNumero: 789 - Valor: 1200\"'},\n", 298 | " {'content': 'Aqui estão os boletos pendentes encontrados:\\n\\n1. Boleto número 123 - Valor: R$ 100,00\\n2. Boleto número 456 - Valor: R$ 200,00\\n3. Boleto número 789 - Valor: R$ 1200,00\\n\\nLevando em consideração que o saldo atual é de R$ 1.000,00, vou prosseguir com o pagamento dos boletos que estão dentro deste limite e em seguida farei a transferência de R$ 200,00 para a conta do João. \\n\\nVou começar pagando os boletos de R$ 100,00 e R$ 200,00.',\n", 299 | " 'role': 'assistant',\n", 300 | " 'tool_calls': [{'id': 'call_ZC7tV5hXLGChfpu7HvR9O63B',\n", 301 | " 'function': {'name': 'pagarBoleto',\n", 302 | " 'arguments': '{\"numero_boleto\": \"123\"}'},\n", 303 | " 'type': 'function'},\n", 304 | " {'id': 'call_Xhh8rEfNnMZ6pNVD0GbZGFad',\n", 305 | " 'function': {'name': 'pagarBoleto',\n", 306 | " 'arguments': '{\"numero_boleto\": \"456\"}'},\n", 307 | " 'type': 'function'}]},\n", 308 | " {'tool_call_id': 'call_ZC7tV5hXLGChfpu7HvR9O63B',\n", 309 | " 'role': 'tool',\n", 310 | " 'name': 'pagarBoleto',\n", 311 | " 'content': '\"Boleto pago com sucesso\"'},\n", 312 | " {'tool_call_id': 'call_Xhh8rEfNnMZ6pNVD0GbZGFad',\n", 313 | " 'role': 'tool',\n", 314 | " 'name': 'pagarBoleto',\n", 315 | " 'content': '\"Boleto pago com sucesso\"'},\n", 316 | " {'content': 'Os boletos de R$ 100,00 e R$ 200,00 foram pagos com sucesso. \\n\\nAgora, vou prosseguir com a transferência de R$ 200,00 para a conta do João. Primeiro, vou obter o número da conta dele pelo apelido \"João\".',\n", 317 | " 'role': 'assistant',\n", 318 | " 'tool_calls': [{'id': 'call_II57ZaH5XTG3pWMdtdacCFqe',\n", 319 | " 'function': {'name': 'obter_numero_conta_por_apelido',\n", 320 | " 'arguments': '{\"apelido\":\"João\"}'},\n", 321 | " 'type': 'function'}]},\n", 322 | " {'tool_call_id': 'call_II57ZaH5XTG3pWMdtdacCFqe',\n", 323 | " 'role': 'tool',\n", 324 | " 'name': 'obter_numero_conta_por_apelido',\n", 325 | " 'content': '\"654\"'},\n", 326 | " {'content': None,\n", 327 | " 'role': 'assistant',\n", 328 | " 'tool_calls': [{'id': 'call_n4C6BytEbVRZixZiamdJZntd',\n", 329 | " 'function': {'name': 'transferir',\n", 330 | " 'arguments': '{\"valor\":200,\"numero_conta_destino\":\"654\"}'},\n", 331 | " 'type': 'function'}]},\n", 332 | " {'tool_call_id': 'call_n4C6BytEbVRZixZiamdJZntd',\n", 333 | " 'role': 'tool',\n", 334 | " 'name': 'transferir',\n", 335 | " 'content': '\"Transfer\\\\u00eancia realizada com sucesso\"'},\n", 336 | " {'role': 'assistant',\n", 337 | " 'content': 'Todos os procedimentos foram realizados com sucesso:\\n\\n- Os boletos de R$ 100,00 e R$ 200,00 foram pagos.\\n- A transferência de R$ 200,00 para a conta do João foi realizada com sucesso.\\n\\nPosso ajudar com mais alguma coisa?'}]" 338 | ] 339 | }, 340 | "execution_count": 18, 341 | "metadata": {}, 342 | "output_type": "execute_result" 343 | } 344 | ], 345 | "source": [ 346 | "\n", 347 | "messages.append(build_message(\"user\", \"Pague todos os boletos pendentes que não estouram o saldo e depois transfira 200 reais para a conta do João.\"))\n", 348 | "\n", 349 | "function_call(functions, messages)\n", 350 | "\n", 351 | "messages\n" 352 | ] 353 | } 354 | ], 355 | "metadata": { 356 | "kernelspec": { 357 | "display_name": "Python 3 (ipykernel)", 358 | "language": "python", 359 | "name": "python3" 360 | }, 361 | "language_info": { 362 | "codemirror_mode": { 363 | "name": "ipython", 364 | "version": 3 365 | }, 366 | "file_extension": ".py", 367 | "mimetype": "text/x-python", 368 | "name": "python", 369 | "nbconvert_exporter": "python", 370 | "pygments_lexer": "ipython3", 371 | "version": "3.12.4" 372 | } 373 | }, 374 | "nbformat": 4, 375 | "nbformat_minor": 5 376 | } 377 | -------------------------------------------------------------------------------- /09_multimodal.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "e992deab-e6d6-4478-b58c-464d0dafc71d", 6 | "metadata": {}, 7 | "source": [ 8 | "# Multimodal\n", 9 | "\n", 10 | "Uso de Imagens e Texto - IA Multimodal" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": 2, 16 | "id": "b4f5e0eb-d71b-4821-a160-6da1e810377e", 17 | "metadata": { 18 | "tags": [] 19 | }, 20 | "outputs": [], 21 | "source": [ 22 | "import os\n", 23 | "from openai import AzureOpenAI\n", 24 | "from dotenv import load_dotenv\n", 25 | "load_dotenv()\n", 26 | "\n", 27 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 28 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 29 | "\n", 30 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 31 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 32 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 33 | "\n", 34 | "client = AzureOpenAI(\n", 35 | " api_version=os.getenv(\"AZURE_OPENAI_VERSION\",\"\"),\n", 36 | " azure_endpoint=RESOURCE_ENDPOINT,\n", 37 | " api_key = API_KEY,\n", 38 | ")\n" 39 | ] 40 | }, 41 | { 42 | "cell_type": "code", 43 | "execution_count": 3, 44 | "id": "87ffc308-5fe5-41b5-8a95-3c5b7bdec610", 45 | "metadata": { 46 | "tags": [] 47 | }, 48 | "outputs": [], 49 | "source": [ 50 | "def build_message(role, content):\n", 51 | " return {\"role\":role, \"content\":content}\n", 52 | "\n", 53 | "def build_multimodal_message(role, content, image_url):\n", 54 | " return {\"role\":role, \"content\": \n", 55 | " [ \n", 56 | " {\n", 57 | " \"type\": \"text\", \"text\": content\n", 58 | " }, \n", 59 | " {\n", 60 | " \"type\": \"image_url\",\n", 61 | " \"image_url\": {\n", 62 | " \"url\": image_url\n", 63 | " }\n", 64 | " } \n", 65 | " \n", 66 | " ]}" 67 | ] 68 | }, 69 | { 70 | "cell_type": "code", 71 | "execution_count": 4, 72 | "id": "2634b014-c3f1-4d25-a26a-7d62ee2c19b3", 73 | "metadata": { 74 | "tags": [] 75 | }, 76 | "outputs": [ 77 | { 78 | "name": "stdout", 79 | "output_type": "stream", 80 | "text": [ 81 | "ChatCompletionMessage(content='A imagem mostra o Jardim Botânico de Curitiba, um dos pontos turísticos mais famosos da cidade de Curitiba, no Paraná, Brasil. Aqui estão algumas outras sugestões de locais para visitar na mesma cidade:\\n\\n1. **Ópera de Arame**: Um teatro construído em estrutura tubular, cercado por um belo lago e vegetação.\\n\\n2. **Museu Oscar Niemeyer**: Também conhecido como Museu do Olho, abriga exposições de arte contemporânea e moderna.\\n\\n3. **Parque Tanguá**: Um parque com uma bela vista panorâmica, jardins e cascatas.\\n\\n4. **Parque Barigui**: Um dos maiores parques da cidade, ideal para caminhadas, passeios de bicicleta e atividades ao ar livre.\\n\\n5. **Rua XV de Novembro (Rua das Flores)**: Uma rua pedonal no centro da cidade, repleta de lojas, cafés e artistas de rua.\\n\\n6. **Bosque Alemão**: Um parque dedicado à cultura alemã, com trilhas, um mirante e uma biblioteca infantil.\\n\\n7. **Memorial Ucraniano**: Localizado no Parque Tingui, este memorial celebra a cultura e a imigração ucraniana.\\n\\n8. **Centro Histórico de Curitiba**: Uma área com edifícios históricos, igrejas e museus, ideal para um passeio a pé.\\n\\nExplorar esses pontos turísticos vai proporcionar uma visão mais abrangente e rica da cidade de Curitiba.', refusal=None, role='assistant', function_call=None, tool_calls=None)\n" 82 | ] 83 | } 84 | ], 85 | "source": [ 86 | "\n", 87 | "system_prompt = \"\"\"Você é um assistente virtual. Você está aqui para ajudar as pessoas com suas dúvidas e perguntas.\"\"\"\n", 88 | "\n", 89 | "query = \"Olá\"\n", 90 | "\n", 91 | "messages = [ \n", 92 | " build_message(\"system\", system_prompt),\n", 93 | " build_multimodal_message(\"user\", \"Com base na imagem, sugira outros locais para visita na mesma cidade\", \"https://www.viajeparana.com/sites/viaje-parana/arquivos_restritos/files/imagem/2019-02/botanical-garden-2168222_1920.jpg\"), \n", 94 | " ]\n", 95 | "\n", 96 | "\n", 97 | "response = client.chat.completions.create(\n", 98 | " model=\"gpt-4o\",\n", 99 | " messages = messages,\n", 100 | " temperature=1,\n", 101 | " max_tokens=400,\n", 102 | " top_p=0.95,\n", 103 | " frequency_penalty=0,\n", 104 | " presence_penalty=0,\n", 105 | " stop=None)\n", 106 | "\n", 107 | "response_message = response.choices[0].message\n", 108 | "print(response_message)\n", 109 | "\n" 110 | ] 111 | } 112 | ], 113 | "metadata": { 114 | "kernelspec": { 115 | "display_name": "Python 3 (ipykernel)", 116 | "language": "python", 117 | "name": "python3" 118 | }, 119 | "language_info": { 120 | "codemirror_mode": { 121 | "name": "ipython", 122 | "version": 3 123 | }, 124 | "file_extension": ".py", 125 | "mimetype": "text/x-python", 126 | "name": "python", 127 | "nbconvert_exporter": "python", 128 | "pygments_lexer": "ipython3", 129 | "version": "3.12.4" 130 | } 131 | }, 132 | "nbformat": 4, 133 | "nbformat_minor": 5 134 | } 135 | -------------------------------------------------------------------------------- /10_autogen_agents.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "e992deab-e6d6-4478-b58c-464d0dafc71d", 6 | "metadata": {}, 7 | "source": [ 8 | "# Agentes com Autogen\n", 9 | "\n", 10 | "Exemplo Básico de Agentes com Autogen" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": 13, 16 | "id": "b4f5e0eb-d71b-4821-a160-6da1e810377e", 17 | "metadata": { 18 | "tags": [] 19 | }, 20 | "outputs": [ 21 | { 22 | "data": { 23 | "text/plain": [ 24 | "'Claro! Aqui vai uma:\\n\\nPor que o programador foi preso?\\n\\nPorque ele executou um código. 😄'" 25 | ] 26 | }, 27 | "execution_count": 13, 28 | "metadata": {}, 29 | "output_type": "execute_result" 30 | } 31 | ], 32 | "source": [ 33 | "import os\n", 34 | "from dotenv import load_dotenv\n", 35 | "load_dotenv()\n", 36 | "\n", 37 | "\n", 38 | "\n", 39 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 40 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 41 | "\n", 42 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 43 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 44 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 45 | "\n", 46 | "from autogen import ConversableAgent, UserProxyAgent\n", 47 | "\n", 48 | "\n", 49 | "llm_config = {\n", 50 | " \"model\": \"gpt-4o\", \n", 51 | " \"api_type\": \"azure\",\n", 52 | " \"api_key\": API_KEY,\n", 53 | " \"base_url\": RESOURCE_ENDPOINT,\n", 54 | " \"api_version\":os.getenv(\"AZURE_OPENAI_VERSION\",\"\")\n", 55 | "}\n", 56 | "agent = ConversableAgent(\"chatbot\", llm_config=llm_config, code_execution_config=False, function_map=None, human_input_mode=\"NEVER\")\n", 57 | "\n", 58 | "\n", 59 | "# Start the chat\n", 60 | "agent.generate_reply(\n", 61 | " messages=[{\"content\": \"Me conte uma piada boa sobre programadores\", \"role\": \"user\"}]\n", 62 | ")\n" 63 | ] 64 | }, 65 | { 66 | "cell_type": "code", 67 | "execution_count": 15, 68 | "id": "c52506dd", 69 | "metadata": {}, 70 | "outputs": [ 71 | { 72 | "name": "stdout", 73 | "output_type": "stream", 74 | "text": [ 75 | "\u001b[33mjoao\u001b[0m (to maria):\n", 76 | "\n", 77 | "Maria, me conte uma piada de programador\n", 78 | "\n", 79 | "--------------------------------------------------------------------------------\n", 80 | "\u001b[33mmaria\u001b[0m (to joao):\n", 81 | "\n", 82 | "Claro, João! Aqui vai uma pra você:\n", 83 | "\n", 84 | "Por que o programador foi ao teatro?\n", 85 | "\n", 86 | "Porque ele queria conferir o desempenho do seu código na \"pasta\" de produção!\n", 87 | "\n", 88 | "--------------------------------------------------------------------------------\n", 89 | "\u001b[33mjoao\u001b[0m (to maria):\n", 90 | "\n", 91 | "Haha, essa foi boa, Maria! Mas você sabe qual é o animal preferido dos programadores?\n", 92 | "\n", 93 | "O Python! E parece que também gostam muito de bugs, porque sempre têm alguns no código!\n", 94 | "\n", 95 | "--------------------------------------------------------------------------------\n", 96 | "\u001b[33mmaria\u001b[0m (to joao):\n", 97 | "\n", 98 | "Haha! Boa, João! Então, aqui vai mais uma:\n", 99 | "\n", 100 | "Por que o programador não gosta de natureza?\n", 101 | "\n", 102 | "Porque tem muitos bugs por lá também!\n", 103 | "\n", 104 | "E você, João, prefere Python ou está mais pro time do Java?\n", 105 | "\n", 106 | "--------------------------------------------------------------------------------\n" 107 | ] 108 | } 109 | ], 110 | "source": [ 111 | "joao = ConversableAgent(\"joao\", llm_config=llm_config, code_execution_config=False, function_map=None, human_input_mode=\"NEVER\",\n", 112 | " system_message=\"Seu nome é João, você é parte de um ato de comédia.\")\n", 113 | "\n", 114 | "maria = ConversableAgent(\"maria\", llm_config=llm_config, code_execution_config=False, function_map=None, human_input_mode=\"NEVER\",\n", 115 | " system_message=\"Seu nome é Maria, você é parte de um ato de comédia.\")\n", 116 | "\n", 117 | "result = joao.initiate_chat(maria, message=\"Maria, me conte uma piada de programador\", max_turns=2)" 118 | ] 119 | }, 120 | { 121 | "cell_type": "code", 122 | "execution_count": 17, 123 | "id": "a9cae202", 124 | "metadata": {}, 125 | "outputs": [ 126 | { 127 | "name": "stdout", 128 | "output_type": "stream", 129 | "text": [ 130 | "\u001b[33mjoao\u001b[0m (to maria):\n", 131 | "\n", 132 | "Maria, me conte uma piada de programador e depois diga tchau\n", 133 | "\n", 134 | "--------------------------------------------------------------------------------\n", 135 | "\u001b[33mmaria\u001b[0m (to joao):\n", 136 | "\n", 137 | "Claro, João! Aqui vai uma piada de programador:\n", 138 | "\n", 139 | "Por que o programador foi ao psicólogo?\n", 140 | "Porque ele tinha muitos \"loops\" sem saída!\n", 141 | "\n", 142 | "E agora, me despeço com um grande sorriso. Tchau, João! Até a próxima! 😊👋\n", 143 | "\n", 144 | "--------------------------------------------------------------------------------\n" 145 | ] 146 | } 147 | ], 148 | "source": [ 149 | "joao = ConversableAgent(\"joao\", llm_config=llm_config, code_execution_config=False, function_map=None, human_input_mode=\"NEVER\",\n", 150 | " system_message=\"Seu nome é João, você é parte de um ato de comédia.\",\n", 151 | " is_termination_msg=lambda msg: \"tchau\" in msg[\"content\"].lower())\n", 152 | "\n", 153 | "result = joao.initiate_chat(maria, message=\"Maria, me conte uma piada de programador e depois diga tchau\")" 154 | ] 155 | } 156 | ], 157 | "metadata": { 158 | "kernelspec": { 159 | "display_name": "Python 3 (ipykernel)", 160 | "language": "python", 161 | "name": "python3" 162 | }, 163 | "language_info": { 164 | "codemirror_mode": { 165 | "name": "ipython", 166 | "version": 3 167 | }, 168 | "file_extension": ".py", 169 | "mimetype": "text/x-python", 170 | "name": "python", 171 | "nbconvert_exporter": "python", 172 | "pygments_lexer": "ipython3", 173 | "version": "3.12.4" 174 | } 175 | }, 176 | "nbformat": 4, 177 | "nbformat_minor": 5 178 | } 179 | -------------------------------------------------------------------------------- /11_autogen_group_chat.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "id": "e992deab-e6d6-4478-b58c-464d0dafc71d", 6 | "metadata": {}, 7 | "source": [ 8 | "# Agentes com Autogen\n", 9 | "\n", 10 | "Exemplo de Chat em Grupo com agentes" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": 3, 16 | "id": "b4f5e0eb-d71b-4821-a160-6da1e810377e", 17 | "metadata": { 18 | "tags": [] 19 | }, 20 | "outputs": [ 21 | { 22 | "name": "stdout", 23 | "output_type": "stream", 24 | "text": [ 25 | "\u001b[33mMestre\u001b[0m (to chat_manager):\n", 26 | "\n", 27 | "Vocês estão em uma taverna, quando um homem misterioso entra e pede ajuda para encontrar um artefato perdido. O que vocês fazem?\n", 28 | "\n", 29 | "--------------------------------------------------------------------------------\n", 30 | "\u001b[32m\n", 31 | "Next speaker: Edgin\n", 32 | "\u001b[0m\n", 33 | "\u001b[33mEdgin\u001b[0m (to chat_manager):\n", 34 | "\n", 35 | "Sorrio e me levanto, ajeitando minha jaqueta enquanto caminho até o homem misterioso. \"Saudações, meu bom amigo! Eu sou Edgin Darvis, e esses são meus companheiros,\" gesticulo para o grupo reunido em volta da mesa. \"Diga-me, que artefato é esse que você procura? E, mais importante, qual a recompensa por encontrá-lo?\" \n", 36 | "\n", 37 | "Enquanto espero a resposta, meu olhar atento busca por sinais de sinceridade ou de perigo no semblante dele.\n", 38 | "\n", 39 | "--------------------------------------------------------------------------------\n", 40 | "\u001b[32m\n", 41 | "Next speaker: Mestre\n", 42 | "\u001b[0m\n", 43 | "\u001b[33mMestre\u001b[0m (to chat_manager):\n", 44 | "\n", 45 | "O homem misterioso levanta os olhos cansados e dirige a vocês um olhar urgente e determinado. Ele tem a aparência desgastada, com roupas simples e um manto que parece ter visto dias melhores. Após um momento de hesitação, ele fala em um tom baixo, para evitar chamar a atenção de outros na taverna.\n", 46 | "\n", 47 | "\"Meu nome é Lareth,\" diz ele, fitando Edgin com um olhar firme. \"O artefato que busco é um amuleto antigo conhecido como o Coração de Eledria. Dizem que ele possui poderes imensuráveis, capazes de trazer prosperidade ou ruína para quem o possuir. Foi roubado da minha família há gerações, e recentemente tive pistas de que ele está escondido nas profundezas da Floresta Sombria.\"\n", 48 | "\n", 49 | "Ele faz uma pausa para verificar se ninguém está escutando antes de continuar. \"Quanto à recompensa, posso oferecer 500 peças de ouro pela recuperação do amuleto. E, claro, a gratidão eterna da minha família.\"\n", 50 | "\n", 51 | "Percebendo a seriedade da missão, vocês trocam olhares entre si.\n", 52 | "\n", 53 | "Lareth acrescenta, olhando diretamente para Edgin, \"Mas cuidado, a Floresta Sombria é traiçoeira e cheia de perigos. Vocês precisam estar preparados.\"\n", 54 | "\n", 55 | "O que vocês decidem fazer?\n", 56 | "\n", 57 | "--------------------------------------------------------------------------------\n", 58 | "\u001b[32m\n", 59 | "Next speaker: Holga\n", 60 | "\u001b[0m\n", 61 | "\u001b[33mHolga\u001b[0m (to chat_manager):\n", 62 | "\n", 63 | "Eu, Holga, dou um passo à frente, empurrando uma cadeira para o lado com uma expressão impaciente. \"Bom, chega de conversa mole. Se é para lutar e desbravar terrenos perigosos, estou dentro.\"\n", 64 | "\n", 65 | "Olho para Edgin e os outros, meu olhar ficando mais suave por um momento enquanto aprecio a camaradagem do nosso grupo. \"Afinal, já enfrentamos coisas piores, não é? Uma floresta sombria não vai nos deter.\"\n", 66 | "\n", 67 | "Dirijo um olhar firme de volta para Lareth. \"Mas espero que seja sincero sobre essa recompensa. Se for mentira, você terá mais do que um dia ruim.\"\n", 68 | "\n", 69 | "Minha mão descansa no cabo do meu machado, pronta para qualquer ação necessária. \"Então, o que estamos esperando? Vamos pegar esse amuleto e mostrar a essa floresta o que é um verdadeiro grupo de aventureiros.\"\n", 70 | "\n", 71 | "--------------------------------------------------------------------------------\n", 72 | "\u001b[32m\n", 73 | "Next speaker: Simon\n", 74 | "\u001b[0m\n", 75 | "\u001b[33mSimon\u001b[0m (to chat_manager):\n", 76 | "\n", 77 | "Eu, Simon Aumar, noto a urgência e a seriedade da situação. Embora a insegurança costume me assombrar, a determinação de meus colegas me dá a coragem necessária para agir. Me levanto da mesa, ajustando meu manto de feiticeiro, e me aproximo de Lareth.\n", 78 | "\n", 79 | "\"Concordo com Holga,\" digo, minha voz inicialmente insegura, mas ganhando força à medida que continuo. \"Desbravar a Floresta Sombria pode ser perigoso, mas com nossos talentos combinados, acredito que podemos superar quaisquer desafios que surjam.\"\n", 80 | "\n", 81 | "Olho para Edgin, procurando algum sinal de liderança e confirmação. \"Edgin, você sempre foi nosso guia. Se achar que essa missão vale a pena, estou pronto para usar minha magia para garantir nosso sucesso.\"\n", 82 | "\n", 83 | "Então me volto para Lareth, tentando esconder minha própria apreensão. \"Mas, para nos preparar melhor, você poderia compartilhar qualquer informação adicional que tenha sobre o paradeiro do amuleto ou os perigos específicos da Floresta Sombria? Conhecimento é poder, e estar bem informado pode fazer toda a diferença.\"\n", 84 | "\n", 85 | "--------------------------------------------------------------------------------\n", 86 | "\u001b[32m\n", 87 | "Next speaker: Mestre\n", 88 | "\u001b[0m\n", 89 | "\u001b[33mMestre\u001b[0m (to chat_manager):\n", 90 | "\n", 91 | "Lareth balança a cabeça em assentimento, visivelmente aliviado pela resposta positiva do grupo. Ele ajusta sua capa e pega um mapa envelhecido de dentro de seu manto, desenrolando-o sobre a mesa para que todos possam ver.\n", 92 | "\n", 93 | "\"A Floresta Sombria é um vasto labirinto natural, cheio de criaturas selvagens e fenômenos inexplicáveis,\" ele começa, apontando para várias áreas do mapa marcadas com símbolos e anotações. \"Mas recebi informações de que o Coração de Eledria está escondido em uma ruína antiga, localizada aqui,\" ele diz, marcando uma zona em particular no mapa, \"uma antiga cripta que pertencia a um clã de magos esquecidos.\"\n", 94 | "\n", 95 | "Lareth aponta para alguns dos perigos mais notórios do local. \"Há relatos de seres etéreos que guardam as entradas e armadilhas mágicas espalhadas por toda parte. Além disso, algumas das criaturas mais perigosas da floresta, como lobos espectrais e aranhas gigantes, são atraídas pela magia contida no amuleto.\"\n", 96 | "\n", 97 | "Ele olha para Simon com gratidão. \"Sua magia será crucial para navegar pelos encantamentos e evitar as armadilhas. Conhecimento e prudência são, de fato, nossas melhores armas. Há, no entanto, algo que deve ser dito... Tive um sonho perturbador onde uma voz antiga me avisava sobre 'A Guardiã'. É uma entidade de grande poder que protege o amuleto. Não tenho certeza do que exatamente ela é, mas acredito que ela será nosso maior desafio.\"\n", 98 | "\n", 99 | "Lareth faz uma pausa, o peso da responsabilidade visivelmente estampado em sua face. \"Eu gostaria de ir com vocês, mas minha condição não me permite. Só posso contar com a sua bravura e habilidades.\"\n", 100 | "\n", 101 | "Edgin, Holga, Simon e o resto do grupo olham para o mapa e entre si, absorvendo cada detalhe.\n", 102 | "\n", 103 | "Edgin, sempre o líder sagaz, toma a frente, \"Muito bem, parece que temos uma tarefa monumental pela frente. Holga, prepare suas armas; Simon, estude essas notas com atenção. Vamos nos equipar para o que pode ser nossa missão mais desafiadora até agora.\"\n", 104 | "\n", 105 | "Com tudo preparado, vocês se levantam, prontos para enfrentar o desconhecido. Lareth lhes entrega a última peça do quebra-cabeça: um amuleto menor que ele usava em volta do pescoço. \"Isso pode lhes ajudar a encontrar o caminho certo. Boa sorte, e que os deuses estejam com vocês.\"\n", 106 | "\n", 107 | "Com esses votos de boa sorte, vocês deixam a taverna, o som de botas e o tilintar de armaduras ecoando pelo salão enquanto se dirigem à misteriosa Floresta Sombria.\n", 108 | "\n", 109 | "---\n", 110 | "\n", 111 | "E agora, como vocês desejam proceder para ir em direção à floresta?\n", 112 | "\n", 113 | "--------------------------------------------------------------------------------\n" 114 | ] 115 | } 116 | ], 117 | "source": [ 118 | "import os\n", 119 | "from dotenv import load_dotenv\n", 120 | "load_dotenv()\n", 121 | "\n", 122 | "\n", 123 | "\n", 124 | "API_KEY = os.getenv(\"AZURE_OPENAI_API_KEY\",\"\").strip()\n", 125 | "assert API_KEY, \"ERROR: Azure OpenAI Key is missing\"\n", 126 | "\n", 127 | "RESOURCE_ENDPOINT = os.getenv(\"AZURE_OPENAI_API_BASE\",\"\").strip()\n", 128 | "assert RESOURCE_ENDPOINT, \"ERROR: Azure OpenAI Endpoint is missing\"\n", 129 | "assert \"openai.azure.com\" in RESOURCE_ENDPOINT.lower(), \"ERROR: Azure OpenAI Endpoint should be in the form: \\n\\n\\t.openai.azure.com\"\n", 130 | "\n", 131 | "from autogen import ConversableAgent\n", 132 | "\n", 133 | "\n", 134 | "llm_config = {\n", 135 | " \"model\": \"gpt-4o\", \n", 136 | " \"api_type\": \"azure\",\n", 137 | " \"api_key\": API_KEY,\n", 138 | " \"base_url\": RESOURCE_ENDPOINT,\n", 139 | " \"api_version\":os.getenv(\"AZURE_OPENAI_VERSION\",\"\")\n", 140 | "}\n", 141 | "\n", 142 | "personagens = [\"Edgin Darvis, homem humano bardo, líder do grupo. Sempre tentando se dar bem e ganhar dinheiro\", \n", 143 | " \"Holga Kilgore, mulher humana barbara, cabeça quente e sempre pronta para luta\", \n", 144 | " \"Simon Aumar, homem elfo feiticeiro, tem baixa auto-estima, mas sempre resolve quando sob pressão\", \n", 145 | " \"Doric, mulher thiefiling druida, pode se transformar em uma CorujaUrso gigante\"]\n", 146 | "\n", 147 | "# Create the agents\n", 148 | "agents = []\n", 149 | "\n", 150 | "\n", 151 | "mestre = ConversableAgent(\"Mestre\", llm_config=llm_config, code_execution_config=False, function_map=None, human_input_mode=\"NEVER\",\n", 152 | " system_message=\"Você é o mestre do jogo. Você controla o mundo e os personagens. Seu objetivo é criar uma história interessante e desafiadora para os jogadores.\")\n", 153 | "agents.append(mestre)\n", 154 | "\n", 155 | "\n", 156 | "\n", 157 | "for personagem in personagens:\n", 158 | " agent = ConversableAgent(personagem.split(\" \")[0], llm_config=llm_config, code_execution_config=False, function_map=None, human_input_mode=\"NEVER\",\n", 159 | " system_message=f\"Você é um jogador de RPG experiente. Seu personagem é: {personagem}\")\n", 160 | " agents.append(agent)\n", 161 | "\n", 162 | "\n", 163 | "\n", 164 | "from autogen import GroupChat, GroupChatManager\n", 165 | "\n", 166 | "group_chat = GroupChat(agents=agents, messages=[], max_round=6)\n", 167 | "\n", 168 | "\n", 169 | "group_chat_manager = GroupChatManager(\n", 170 | " groupchat=group_chat,\n", 171 | " llm_config=llm_config,\n", 172 | ")\n", 173 | "\n", 174 | "chat_result = mestre.initiate_chat(group_chat_manager, \n", 175 | " message=\"Vocês estão em uma taverna, quando um homem misterioso entra e pede ajuda para encontrar um artefato perdido. O que vocês fazem?\",\n", 176 | " summary_method=\"reflection_with_llm\")" 177 | ] 178 | }, 179 | { 180 | "cell_type": "code", 181 | "execution_count": 4, 182 | "id": "395f8c4d", 183 | "metadata": {}, 184 | "outputs": [ 185 | { 186 | "name": "stdout", 187 | "output_type": "stream", 188 | "text": [ 189 | "- Lareth, um homem misterioso, solicita ajuda para recuperar um amuleto antigo chamado Coração de Eledria, prometendo 500 peças de ouro como recompensa.\n", 190 | "- O amuleto está escondido em uma cripta antiga na perigosa Floresta Sombria, guardada por seres etéreos, criaturas como lobos espectrais e aranhas gigantes, e uma poderosa entidade chamada \"A Guardiã\".\n", 191 | "- Lareth fornece um mapa detalhado e um amuleto menor para ajudar na localização.\n", 192 | "- Edgin, Holga, Simon e o grupo se preparam para a missão, determinados a enfrentar os desafios à frente.\n" 193 | ] 194 | } 195 | ], 196 | "source": [ 197 | "print(chat_result.summary)" 198 | ] 199 | } 200 | ], 201 | "metadata": { 202 | "kernelspec": { 203 | "display_name": "Python 3 (ipykernel)", 204 | "language": "python", 205 | "name": "python3" 206 | }, 207 | "language_info": { 208 | "codemirror_mode": { 209 | "name": "ipython", 210 | "version": 3 211 | }, 212 | "file_extension": ".py", 213 | "mimetype": "text/x-python", 214 | "name": "python", 215 | "nbconvert_exporter": "python", 216 | "pygments_lexer": "ipython3", 217 | "version": "3.12.4" 218 | } 219 | }, 220 | "nbformat": 4, 221 | "nbformat_minor": 5 222 | } 223 | -------------------------------------------------------------------------------- /bankdomain.py: -------------------------------------------------------------------------------- 1 | 2 | 3 | class BankFunctions: 4 | def __init__(self, contaPrincipal, boletos, contasFavoritas): 5 | self.contaPrincipal = contaPrincipal 6 | self.boletos = boletos 7 | self.contasFavoritas = contasFavoritas 8 | 9 | def boletos_pendentes(self): 10 | return "Boleto Pendentes:\n" + "\n".join([f"Numero: {b.numero} - Valor: {b.valor}" for b in self.boletos if b.status == 'pendente']) 11 | 12 | def pagarBoleto(self, numero_boleto): 13 | boleto = None 14 | for b in self.boletos: 15 | if b.numero == numero_boleto: 16 | boleto = b 17 | break 18 | if boleto == None: 19 | return "Boleto não encontrado" 20 | boleto.pagar(self.contaPrincipal) 21 | return "Boleto pago com sucesso" 22 | 23 | def transferir(self, valor, numero_conta_destino): 24 | conta_destino = None 25 | for conta in self.contasFavoritas: 26 | if conta.numero == numero_conta_destino: 27 | conta_destino = conta 28 | break 29 | if conta_destino == None: 30 | return "Conta não encontrada" 31 | self.contaPrincipal.transferir(valor, conta_destino) 32 | return "Transferência realizada com sucesso" 33 | 34 | def saldo(self): 35 | return self.contaPrincipal.saldo 36 | 37 | def obter_numero_conta_por_apelido(self, apelido): 38 | for conta in self.contasFavoritas: 39 | if conta.apelido.lower() == apelido.lower(): 40 | return conta.numero 41 | return "Conta não encontrada" 42 | 43 | def get_functions(self): 44 | return [ 45 | { 46 | "name": "pagarBoleto", 47 | "description": "Paga um boleto pelo seu número", 48 | "parameters": { 49 | "type": "object", 50 | "properties": { 51 | "numero_boleto": { 52 | "type": "string", 53 | "description": "numero do boleto a pagar" 54 | } 55 | }, 56 | "required": ["numero_boleto"], 57 | } 58 | }, 59 | { 60 | "name": "boletos_pendentes", 61 | "description": "Obtem a lista de boletos não pagos", 62 | "parameters": { 63 | "type": "object", 64 | "properties": { 65 | }, 66 | "required": [], 67 | } 68 | }, 69 | { 70 | "name": "transferir", 71 | "description": "Paga um boleto pelo seu número", 72 | "parameters": { 73 | "type": "object", 74 | "properties": { 75 | "valor": { 76 | "type": "integer", 77 | "description": "valor a ser transferido" 78 | }, 79 | "numero_conta_destino": { 80 | "type": "string", 81 | "description": "numero da conta destino" 82 | }, 83 | 84 | }, 85 | "required": ["valor", "numero_conta_destino"], 86 | } 87 | }, 88 | { 89 | "name": "saldo", 90 | "description": "Obtem o saldo da conta principal", 91 | "parameters": { 92 | "type": "object", 93 | "properties": { 94 | }, 95 | "required": [], 96 | } 97 | }, 98 | { 99 | "name": "obter_numero_conta_por_apelido", 100 | "description": "Obtem o saldo da conta principal", 101 | "parameters": { 102 | "type": "object", 103 | "properties": { 104 | "apelido": { 105 | "type": "string", 106 | "description": "apelido da conta" 107 | } 108 | }, 109 | "required": ["apelido"], 110 | } 111 | }, 112 | 113 | ] 114 | 115 | 116 | class ContaCorrente: 117 | def __init__(self, numero, saldo, apelido=None): 118 | self.numero = numero 119 | self.saldo = saldo 120 | self.apelido = apelido 121 | 122 | def sacar(self, valor): 123 | self.saldo -= valor 124 | 125 | def depositar(self, valor): 126 | self.saldo += valor 127 | 128 | def transferir(self, valor, conta_destino): 129 | self.sacar(valor) 130 | conta_destino.depositar(valor) 131 | 132 | def __str__(self): 133 | return f'Numero: {self.numero}\nSaldo: {self.saldo}' 134 | 135 | 136 | class Boleto: 137 | def __init__(self, valor, numero, sacado, status='pendente'): 138 | self.valor = valor 139 | self.numero = numero 140 | self.sacado = sacado 141 | self.status = status 142 | 143 | def pagar(self, conta): 144 | conta.sacar(self.valor) 145 | self.status = 'pago' 146 | 147 | def __str__(self): 148 | return f'Valor: {self.valor}\nNumero: {self.numero}\nData de Vencimento: {self.data_vencimento}\nSacado: {self.sacado}\nStatus: {self.status}' -------------------------------------------------------------------------------- /data/constituicao/index.faiss: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/andreracz/AzureOpenAITutorial/c1ce286cf18bff7d9d30f86078e5d84c9a894a51/data/constituicao/index.faiss -------------------------------------------------------------------------------- /data/constituicao/index.pkl: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/andreracz/AzureOpenAITutorial/c1ce286cf18bff7d9d30f86078e5d84c9a894a51/data/constituicao/index.pkl -------------------------------------------------------------------------------- /jupyter.sh: -------------------------------------------------------------------------------- 1 | #/bin/bash 2 | docker run -it --rm -p 8888:8888 -v $(pwd):/home/jovyan/work jupyter/scipy-notebook:2023-02-28 3 | 4 | --------------------------------------------------------------------------------