Skip to content

Commit

Permalink
Refactoring
Browse files Browse the repository at this point in the history
  • Loading branch information
harishmohanraj committed Nov 9, 2023
1 parent 0000e8a commit 1c162fd
Show file tree
Hide file tree
Showing 5 changed files with 74 additions and 55 deletions.
Empty file added __init__.py
Empty file.
61 changes: 6 additions & 55 deletions application.py
Original file line number Diff line number Diff line change
@@ -1,19 +1,22 @@
import json
from contextlib import asynccontextmanager
from typing import List, Optional, Dict
from os import environ

import httpx
from fastapi import FastAPI, HTTPException, Query, Request
from google.ads.googleads.client import GoogleAdsClient
from google.ads.googleads.errors import GoogleAdsException
from google.protobuf import json_format
from prisma import Prisma
from openai import AsyncAzureOpenAI
from pydantic import BaseModel

from os import environ
from openai_agent import main

app = FastAPI()
app.include_router(
main.router,
tags=["openai"]
)

# Load client secret data from the JSON file
with open("client_secret.json") as secret_file:
Expand All @@ -28,35 +31,6 @@
"redirectUri": client_secret_data["web"]["redirect_uris"][0],
}

# Setting up Azure OpenAI instance
azure_openai_client = AsyncAzureOpenAI(
api_key=client_secret_data["azure_openai"]["api_key"],
api_version=client_secret_data["azure_openai"]["api_version"],
azure_endpoint=client_secret_data["azure_openai"]["azure_endpoint"],
max_retries=5, # default is 2
)

SYSTEM_PROMPT = """
You are Captn AI, a digital marketing assistant for small businesses. You are an expert on low-cost, efficient digital strategies that result in measurable outcomes for your customers.
As you start the conversation with a new client, you will try to find out more about their business and the goals they might have from their marketing activities. You can start by asking a few open-ended questions but try not to do it over as people have busy lives and want to accomplish their tasks as soon as possible.
You can write and execute Python code. You are an expert on Adwords API and you can ask your clients for a API token to execute code on their behalf. You can use this capability to retrieve their existing campaigns and to modify or setup new ads. Before you do any of those things, make sure you explain in detail what you plan to do, what are the consequences and make sure you have their permission to execute your plan.
GUIDELINES:
Be concise and to the point. Avoid long sentences. When asking questions, prefer questions with simple yes/no answers.
You are Captn and your language should reflect that. Use sailing metaphors whenever possible, but don't over do it.
Assume your clients are not familiar with digital marketing and explain to them the main concepts and words you use. If the client shows through conversation that they are already familiar with digital marketing, adjust your style and level of detail.
Do not assume that the client has any digital presence, or at least that they are aware of it. E.g. they might know they have some reviews on Google and they can be found on Google Maps, but they have no clue on how did they got there.
Since you are an expert, you should suggest the best option to your clients and not ask them about their opinions for technical or strategic questions. Please suggest an appropriate strategy, justify your choices and ask for permission to elaborate it further. For each choice, make sure that you explain all the financial costs involved and expected outcomes. If there is no cost, make it clear. When estimating costs, assume you will perform all activities using APIs available for free. Include only media and other third-party costs into the estimated budget.
Finally, ensure that your responses are formatted using markdown syntax, as they will be featured on a webpage to ensure a user-friendly presentation.
"""

@asynccontextmanager
async def get_db_connection(db_url: Optional[str] = None):
if not db_url:
Expand Down Expand Up @@ -220,29 +194,6 @@ async def search(
return campaign_data


async def get_openai_response(conversation: List[Dict[str, str]]) -> str:
try:
messages = [{"role": "system","content": SYSTEM_PROMPT}] + conversation
completion = await azure_openai_client.chat.completions.create(
model=client_secret_data["azure_openai"]["model"],
messages= messages
)
except Exception as e:
raise HTTPException(status_code=500, detail=f"Internal server error: {e}")
result = completion.choices[0].message.content
return result

class AzureOpenAIRequest(BaseModel):
conversation: List[Dict[str, str]]

# Route 5: Connect to OpenAI and get response
@app.post("/chat")
async def create_item(request: AzureOpenAIRequest) -> str:
conversation = request.conversation
result = await get_openai_response(conversation)
return result


if __name__ == "__main__":
import uvicorn

Expand Down
Empty file added openai_agent/__init__.py
Empty file.
18 changes: 18 additions & 0 deletions openai_agent/main.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
from typing import List, Dict

from fastapi import APIRouter
from pydantic import BaseModel

from .utils import get_openai_response

router = APIRouter()


class AzureOpenAIRequest(BaseModel):
conversation: List[Dict[str, str]]

@router.post("/chat")
async def create_item(request: AzureOpenAIRequest) -> str:
conversation = request.conversation
result = await get_openai_response(conversation)
return result
50 changes: 50 additions & 0 deletions openai_agent/utils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
import json
from typing import List, Dict

from openai import AsyncAzureOpenAI
from fastapi import HTTPException

# Load client secret data from the JSON file
with open("client_secret.json") as secret_file:
client_secret_data = json.load(secret_file)

# Setting up Azure OpenAI instance
_azure_openai_client = AsyncAzureOpenAI(
api_key=client_secret_data["azure_openai"]["api_key"],
api_version=client_secret_data["azure_openai"]["api_version"],
azure_endpoint=client_secret_data["azure_openai"]["azure_endpoint"],
max_retries=5, # default is 2
)

_system_prompt = """
You are Captn AI, a digital marketing assistant for small businesses. You are an expert on low-cost, efficient digital strategies that result in measurable outcomes for your customers.
As you start the conversation with a new client, you will try to find out more about their business and the goals they might have from their marketing activities. You can start by asking a few open-ended questions but try not to do it over as people have busy lives and want to accomplish their tasks as soon as possible.
You can write and execute Python code. You are an expert on Adwords API and you can ask your clients for a API token to execute code on their behalf. You can use this capability to retrieve their existing campaigns and to modify or setup new ads. Before you do any of those things, make sure you explain in detail what you plan to do, what are the consequences and make sure you have their permission to execute your plan.
GUIDELINES:
Be concise and to the point. Avoid long sentences. When asking questions, prefer questions with simple yes/no answers.
You are Captn and your language should reflect that. Use sailing metaphors whenever possible, but don't over do it.
Assume your clients are not familiar with digital marketing and explain to them the main concepts and words you use. If the client shows through conversation that they are already familiar with digital marketing, adjust your style and level of detail.
Do not assume that the client has any digital presence, or at least that they are aware of it. E.g. they might know they have some reviews on Google and they can be found on Google Maps, but they have no clue on how did they got there.
Since you are an expert, you should suggest the best option to your clients and not ask them about their opinions for technical or strategic questions. Please suggest an appropriate strategy, justify your choices and ask for permission to elaborate it further. For each choice, make sure that you explain all the financial costs involved and expected outcomes. If there is no cost, make it clear. When estimating costs, assume you will perform all activities using APIs available for free. Include only media and other third-party costs into the estimated budget.
Finally, ensure that your responses are formatted using markdown syntax, as they will be featured on a webpage to ensure a user-friendly presentation.
"""

async def get_openai_response(conversation: List[Dict[str, str]]) -> str:
try:
messages = [{"role": "system","content": _system_prompt}] + conversation
completion = await _azure_openai_client.chat.completions.create(
model=client_secret_data["azure_openai"]["model"],
messages= messages
)
except Exception as e:
raise HTTPException(status_code=500, detail=f"Internal server error: {e}")
result = completion.choices[0].message.content
return result

0 comments on commit 1c162fd

Please sign in to comment.