File size: 9,969 Bytes
848e2ce
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
{
 "cells": [
  {
   "cell_type": "markdown",
   "id": "a71ed017-e1b0-4299-88b3-f0eb05adc4df",
   "metadata": {},
   "source": [
    "# The Price is Right\n",
    "\n",
    "The final step is to build a User Interface\n",
    "\n",
    "We will use more advanced aspects of Gradio - building piece by piece."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "614c6202-4575-448d-98ee-78b735775d2b",
   "metadata": {},
   "outputs": [],
   "source": [
    "import gradio as gr\n",
    "from deal_agent_framework import DealAgentFramework\n",
    "from agents.deals import Opportunity, Deal"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "0534e714-5a9c-45c6-998c-3472ac0bb8b5",
   "metadata": {},
   "outputs": [],
   "source": [
    "with gr.Blocks(title=\"The Price is Right\", fill_width=True) as ui:\n",
    "\n",
    "    with gr.Row():\n",
    "        gr.Markdown('<div style=\"text-align: center;font-size:24px\">The Price is Right - Deal Hunting Agentic AI</div>')\n",
    "    with gr.Row():\n",
    "        gr.Markdown('<div style=\"text-align: center;font-size:14px\">Autonomous agent framework that finds online deals, collaborating with a proprietary fine-tuned LLM deployed on Modal, and a RAG pipeline with a frontier model and Chroma.</div>')\n",
    "        \n",
    "\n",
    "ui.launch(inbrowser=True)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "18c12c10-750c-4da3-8df5-f2bc3393f9e0",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Updated to change from height to max_height due to change in Gradio v5\n",
    "# With much thanks to student Ed B. for raising this\n",
    "\n",
    "with gr.Blocks(title=\"The Price is Right\", fill_width=True) as ui:\n",
    "\n",
    "    initial_deal = Deal(product_description=\"Example description\", price=100.0, url=\"https://cnn.com\")\n",
    "    initial_opportunity = Opportunity(deal=initial_deal, estimate=200.0, discount=100.0)\n",
    "    opportunities = gr.State([initial_opportunity])\n",
    "\n",
    "    def get_table(opps):\n",
    "        return [[opp.deal.product_description, opp.deal.price, opp.estimate, opp.discount, opp.deal.url] for opp in opps]\n",
    "\n",
    "    with gr.Row():\n",
    "        gr.Markdown('<div style=\"text-align: center;font-size:24px\">\"The Price is Right\" - Deal Hunting Agentic AI</div>')\n",
    "    with gr.Row():\n",
    "        gr.Markdown('<div style=\"text-align: center;font-size:14px\">Deals surfaced so far:</div>')\n",
    "    with gr.Row():\n",
    "        opportunities_dataframe = gr.Dataframe(\n",
    "            headers=[\"Description\", \"Price\", \"Estimate\", \"Discount\", \"URL\"],\n",
    "            wrap=True,\n",
    "            column_widths=[4, 1, 1, 1, 2],\n",
    "            row_count=10,\n",
    "            col_count=5,\n",
    "            max_height=400,\n",
    "        )\n",
    "\n",
    "    ui.load(get_table, inputs=[opportunities], outputs=[opportunities_dataframe])\n",
    "\n",
    "ui.launch(inbrowser=True)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "87106328-a17a-447e-90b9-c547613468da",
   "metadata": {},
   "outputs": [],
   "source": [
    "agent_framework = DealAgentFramework()\n",
    "agent_framework.init_agents_as_needed()\n",
    "\n",
    "with gr.Blocks(title=\"The Price is Right\", fill_width=True) as ui:\n",
    "\n",
    "    initial_deal = Deal(product_description=\"Example description\", price=100.0, url=\"https://cnn.com\")\n",
    "    initial_opportunity = Opportunity(deal=initial_deal, estimate=200.0, discount=100.0)\n",
    "    opportunities = gr.State([initial_opportunity])\n",
    "\n",
    "    def get_table(opps):\n",
    "        return [[opp.deal.product_description, opp.deal.price, opp.estimate, opp.discount, opp.deal.url] for opp in opps]\n",
    "\n",
    "    def do_select(opportunities, selected_index: gr.SelectData):\n",
    "        row = selected_index.index[0]\n",
    "        opportunity = opportunities[row]\n",
    "        agent_framework.planner.messenger.alert(opportunity)\n",
    "\n",
    "    with gr.Row():\n",
    "        gr.Markdown('<div style=\"text-align: center;font-size:24px\">\"The Price is Right\" - Deal Hunting Agentic AI</div>')\n",
    "    with gr.Row():\n",
    "        gr.Markdown('<div style=\"text-align: center;font-size:14px\">Deals surfaced so far:</div>')\n",
    "    with gr.Row():\n",
    "        opportunities_dataframe = gr.Dataframe(\n",
    "            headers=[\"Description\", \"Price\", \"Estimate\", \"Discount\", \"URL\"],\n",
    "            wrap=True,\n",
    "            column_widths=[4, 1, 1, 1, 2],\n",
    "            row_count=10,\n",
    "            col_count=5,\n",
    "            max_height=400,\n",
    "        )\n",
    "\n",
    "    ui.load(get_table, inputs=[opportunities], outputs=[opportunities_dataframe])\n",
    "    opportunities_dataframe.select(do_select, inputs=[opportunities], outputs=[])\n",
    "\n",
    "ui.launch(inbrowser=True)"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "ecfed67b-ebcb-4e17-ad15-a7151f940119",
   "metadata": {},
   "source": [
    "# Time for the code\n",
    "\n",
    "And now we'll move to the price_is_right.py code"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "db815f9b",
   "metadata": {},
   "outputs": [],
   "source": [
    "# Reset memory back to 2 deals discovered in the past\n",
    "\n",
    "from deal_agent_framework import DealAgentFramework\n",
    "DealAgentFramework.reset_memory()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "50b5c629",
   "metadata": {},
   "outputs": [],
   "source": [
    "import logging\n",
    "root = logging.getLogger()\n",
    "root.setLevel(logging.INFO)"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "d783af8a-08a8-4e59-886a-7ca32f16bcf5",
   "metadata": {},
   "source": [
    "# Running the final product\n",
    "\n",
    "## Just hit shift + enter in the next cell, and let the deals flow in!!"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "48506465-1c7a-433f-a665-b277a8b4665c",
   "metadata": {},
   "outputs": [],
   "source": [
    "!uv run price_is_right.py"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "242d1243-fbec-4807-988b-8f70c8c9b806",
   "metadata": {},
   "source": [
    "<table style=\"margin: 0; text-align: left;\">\n",
    "    <tr>\n",
    "        <td style=\"width: 150px; height: 150px; vertical-align: middle;\">\n",
    "            <img src=\"../assets/important.jpg\" width=\"150\" height=\"150\" style=\"display: block;\" />\n",
    "        </td>\n",
    "        <td>\n",
    "            <h2 style=\"color:#a22;\">But wait!! There's more..</h2>\n",
    "            <span style=\"color:#a22;\">If you're not fed up of product prices yet 😂 I've built this out some more!<br/>\n",
    "            If you look in my repo <a href=\"https://github.com/ed-donner/tech2ai\">tech2ai</a>, in segment4 is a version that uses OpenAI Agents SDK for the AutonomousPlanningAgent, and makes use of MCP servers.  If you're intrigued by Agents and MCP, and would like to learn more, then I also have a companion course on this. This, along with my 2 other companion courses, are laid out in my <a href=\"https://edwarddonner.com/2025/05/28/connecting-my-courses-become-an-llm-expert-and-leader/\">complete AI curriculum</a>.\n",
    "            </span>\n",
    "        </td>\n",
    "    </tr>\n",
    "</table>"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "331a2044-566f-4866-be4d-7542b7dfdf3f",
   "metadata": {},
   "source": [
    "<table style=\"margin: 0; text-align: left;\">\n",
    "    <tr>\n",
    "        <td style=\"width: 150px; height: 150px; vertical-align: middle;\">\n",
    "            <img src=\"../assets/thankyou.jpg\" width=\"150\" height=\"150\" style=\"display: block;\" />\n",
    "        </td>\n",
    "        <td>\n",
    "            <h2 style=\"color:#090;\">CONGRATULATIONS AND THANK YOU!!!</h2>\n",
    "            <span style=\"color:#090;\">\n",
    "                It's so fabulous that you've made it to the very end! My heartiest congratulations. Please stay in touch! I'm <a href=\"https://www.linkedin.com/in/eddonner/\">here on LinkedIn</a> if we're not already connected and I'm on X at <a href=\"https://x.com/edwarddonner\">@edwarddonner</a>. And my editor would be cross with me if I didn't mention one more time: it makes a HUGE difference when students rate this course on Udemy - it's one of the main ways that Udemy decides whether to show it to others. <br/><br/>Massive thanks again for putting up with me for 8 weeks and getting all the way to the final cell! I'm excited to hear all about your career as an LLM Engineer. If you post on LinkedIn about completing the course and tag me, then I'll weigh in to amplify your achievement. <br/><b>You could not have picked a better time to be in this field.</b>\n",
    "            </span>\n",
    "        </td>\n",
    "    </tr>\n",
    "</table>"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "f9dd0a27-7d46-4c9e-bbe4-a61c9c899c99",
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": ".venv",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.12.12"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}