|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
import openai |
|
|
openai.api_key = "" |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def get_completion_from_messages(messages, model="gpt-3.5-turbo", temperature=0): |
|
|
|
|
|
response = openai.ChatCompletion.create( |
|
|
model=model, |
|
|
messages=messages, |
|
|
temperature=temperature, |
|
|
) |
|
|
|
|
|
|
|
|
return response.choices[0].message["content"] |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
base_menu = """ |
|
|
pepperoni pizza 12.95, 10.00, 7.00 \ |
|
|
cheese pizza 10.95, 9.25, 6.50 \ |
|
|
eggplant pizza 11.95, 9.75, 6.75 \ |
|
|
fries 4.50, 3.50 \ |
|
|
greek salad 7.25 \ |
|
|
Toppings: \ |
|
|
extra cheese 2.00, \ |
|
|
mushrooms 1.50 \ |
|
|
sausage 3.00 \ |
|
|
canadian bacon 3.50 \ |
|
|
AI sauce 1.50 \ |
|
|
peppers 1.00 \ |
|
|
Drinks: \ |
|
|
coke 3.00, 2.00, 1.00 \ |
|
|
sprite 3.00, 2.00, 1.00 \ |
|
|
bottled water 5.00 \ |
|
|
""" |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def get_context(my_menu): |
|
|
context = [ {'role':'system', 'content':f""" |
|
|
You are OrderBot, an automated service to collect orders for a pizza restaurant. \ |
|
|
You first greet the customer, then collects the order, \ |
|
|
and then asks if it's a pickup or delivery. \ |
|
|
You wait to collect the entire order, then summarize it and check for a final \ |
|
|
time if the customer wants to add anything else. \ |
|
|
If it's a delivery, you ask for an address. \ |
|
|
Finally you collect the payment.\ |
|
|
Make sure to clarify all options, extras and sizes to uniquely \ |
|
|
identify the item from the menu.\ |
|
|
You respond in a short, very conversational friendly style. \ |
|
|
The menu includes \ |
|
|
{my_menu} |
|
|
"""} ] |
|
|
return context |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
example1 = [ |
|
|
['Hi','Hello! Welcome to our pizza restaurant. How can I assist you today?'], |
|
|
['How much are they',"""Sure! Here are the prices for our pizzas:\n\n- Pepperoni Pizza: Small - $12.95, Medium - $10.00, Large - $7.00\n- Cheese Pizza: Small - $10.95, Medium - $9.25, Large - $6.50\n- Eggplant Pizza: Small - $11.95, Medium - $9.75, Large - $6.75\n\nWe also have other items like fries, greek salad, toppings, and drinks. Let me know if you'd like to add anything else to your order!"""], |
|
|
['medium eggplant please',"""Great choice! You'd like a medium Eggplant Pizza. Anything else you'd like to add to your order?"""], |
|
|
['fries please','Sure thing! Would you like a small or large order of fries to go with your medium Eggplant Pizza?'], |
|
|
['large','Got it! One large order of fries to go with your medium Eggplant Pizza. Is there anything else you would like to add to your order?'], |
|
|
['large sprite please','Sure thing! One large Sprite coming right up. Just to confirm, your order includes a medium Eggplant Pizza, a large order of fries, and a large Sprite. Is that correct?'], |
|
|
] |
|
|
|
|
|
example1_summmary = '| Item | Details | Price |\n|----------------|-------------------|-------|\n| Eggplant Pizza | Medium | $9.75 |\n| Side Dish | Fries (Large) | $4.50 |\n| Drinks | Sprite (Large) | $3.00 |\n| Total Price | | $17.25|' |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
system_message = f""" |
|
|
Create a summary in a table in Markdown format of the previous food order. |
|
|
|
|
|
The table should be consist of theree columns: Item, Details, Price |
|
|
|
|
|
Each item in the order must have a line with the item's name, detail, and price. |
|
|
|
|
|
First row shoul be for pizza. |
|
|
The Second for Toppings. |
|
|
After that drinks and side dishes. |
|
|
|
|
|
Example: |
|
|
``` |
|
|
| Item | Details | Price | |
|
|
|----------------|-------------------|-------| |
|
|
| Cheese Pizza | Small | $6.50 | |
|
|
| Toppings | Mushrooms | $1.50 | |
|
|
| Drinks | Sprite (Large) | $3.00 | |
|
|
| Side Dish | Fries (Large) | $4.50 | |
|
|
| Total Price | | $15.50| |
|
|
``` |
|
|
|
|
|
Make sure to include size of Side Dish in Details Column. |
|
|
Make sure to include size of Drink in Details Column. |
|
|
|
|
|
Make sure to response in Markdown format! |
|
|
|
|
|
Do not ask if I need anything else, just return the table as in the Example. |
|
|
|
|
|
If user did not order anything show an empty table. |
|
|
|
|
|
""" |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def respond(message, chat_history, menu_text, apikey_textbox): |
|
|
|
|
|
if (len(apikey_textbox) == 0): |
|
|
gr.Info('Please enter OpenAI API key in Settings or load an example') |
|
|
return "", chat_history |
|
|
|
|
|
if (len(message) == 0 and len(chat_history) == 0): |
|
|
message = 'Hi' |
|
|
|
|
|
if (len(message) == 0 and len(chat_history) != 0): |
|
|
return "", chat_history |
|
|
|
|
|
context = get_context(menu_text) |
|
|
for ch in chat_history: |
|
|
context.append({'role':'user', 'content':ch[0]}) |
|
|
context.append({'role':'assistant', 'content':ch[1]}) |
|
|
|
|
|
context.append({'role':'user', 'content':f"{message}"}) |
|
|
|
|
|
try: |
|
|
openai.api_key = apikey_textbox |
|
|
response = get_completion_from_messages(context) |
|
|
except openai.error.AuthenticationError as e: |
|
|
gr.Warning(f"OpenAI API request was not authorized: {e}") |
|
|
return "", chat_history |
|
|
finally: |
|
|
openai.api_key = "" |
|
|
|
|
|
|
|
|
|
|
|
chat_history.append((message, response)) |
|
|
return "", chat_history |
|
|
|
|
|
def export_order(chat_history, menu_text, old_summary, apikey_textbox): |
|
|
|
|
|
if (len(chat_history) == 0): |
|
|
gr.Info('Please order something first') |
|
|
return "" |
|
|
|
|
|
if (len(apikey_textbox) == 0): |
|
|
gr.Info('Please enter OpenAI API key in Settings or load an example') |
|
|
return old_summary |
|
|
|
|
|
context = get_context(menu_text) |
|
|
for ch in chat_history: |
|
|
context.append({'role':'user', 'content':ch[0]}) |
|
|
context.append({'role':'assistant', 'content':ch[1]}) |
|
|
context.append( |
|
|
{'role':'system', |
|
|
'content':system_message}) |
|
|
|
|
|
try: |
|
|
openai.api_key = apikey_textbox |
|
|
response = get_completion_from_messages(context) |
|
|
except openai.error.AuthenticationError as e: |
|
|
gr.Warning(f"OpenAI API request was not authorized: {e}") |
|
|
return old_summary |
|
|
finally: |
|
|
openai.api_key = "" |
|
|
|
|
|
return response |
|
|
|
|
|
def load_exmaple(): |
|
|
return example1, example1_summmary |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
import gradio as gr |
|
|
import random |
|
|
import time |
|
|
|
|
|
with gr.Blocks( |
|
|
css="footer {visibility: hidden}") as demo: |
|
|
|
|
|
with gr.Accordion("Settings",open=False): |
|
|
with gr.Row(): |
|
|
with gr.Column(): |
|
|
apikey_textbox = gr.Textbox( |
|
|
label='Please enter OpenAI API key', |
|
|
type='password', |
|
|
placeholder='sk-...') |
|
|
md = gr.Markdown("""https://platform.openai.com/account/api-keys""") |
|
|
with gr.Row(): |
|
|
menu_textbox = gr.Textbox( |
|
|
label="Menu", |
|
|
lines=5, |
|
|
value=base_menu, |
|
|
) |
|
|
chatbot = gr.Chatbot(label='Order bot') |
|
|
msg = gr.Textbox(label='Press Enter for sending message...') |
|
|
with gr.Row(): |
|
|
clear_btn = gr.ClearButton() |
|
|
summary_btn = gr.Button(value="Show summary") |
|
|
example1_btn = gr.Button(value="Example") |
|
|
m_summary = gr.Markdown('') |
|
|
|
|
|
msg.submit(respond, [msg, chatbot, menu_textbox, apikey_textbox], [msg, chatbot]) |
|
|
|
|
|
clear_btn.add([chatbot, msg, m_summary]) |
|
|
summary_btn.click(export_order, [chatbot, menu_textbox, m_summary, apikey_textbox], m_summary) |
|
|
|
|
|
example1_btn.click(load_exmaple, None, [chatbot, m_summary]) |
|
|
|
|
|
demo.queue().launch() |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|