nagarmayank commited on
Commit
f9314a9
·
1 Parent(s): fa74d4d

changes - logging

Browse files
Files changed (3) hide show
  1. .gitignore +2 -1
  2. app.py +23 -16
  3. requirements.txt +2 -1
.gitignore CHANGED
@@ -1 +1,2 @@
1
- .venv
 
 
1
+ .venv
2
+ .env
app.py CHANGED
@@ -15,8 +15,13 @@ from google.oauth2 import service_account
15
  import os
16
  from langchain_groq import ChatGroq
17
  import groq
 
18
 
19
- sheet_url = os.getenv("SHEET_URL")
 
 
 
 
20
  GOOGLESHEETS_CREDENTIALS = os.getenv("GOOGLESHEETS_CREDENTIALS")
21
  GROQ_API_KEY = os.environ.get("GROQ_API_KEY")
22
  MODEL = "meta-llama/llama-4-scout-17b-16e-instruct"
@@ -24,11 +29,11 @@ MODEL = "meta-llama/llama-4-scout-17b-16e-instruct"
24
  class TransactionParser(BaseModel):
25
  """This Pydantic class is used to parse the transaction message."""
26
 
27
- amount: str = Field(description="The amount of the transaction strictly in decimal format. If the transaction is a credit or a reversal, then include negative sign. Otherwise it should always be positive. DO not insert currency symbol.", example="123.45")
28
  dr_or_cr: str = Field(description="Identify if the transaction was debit (spent) or credit (received). Strictly choose one of the values - Debit or Credit")
29
- receiver: str = Field(description="The recipient of the transaction. Identify the Merchant Name from the value.")
30
  category: str = Field(description="The category of the transaction. The category of the transaction is linked to the Merchant Name. Strictly choose from one the of values - Shopping,EMI,Education,Miscellaneous,Grocery,Utility,House Help,Travel,Transport")
31
- transaction_date: str = Field(description="The date of the transaction strictly in yyyy-mm-dd format. If the year is not provided then use current year.")
32
  transaction_origin: str = Field(description="The origin of the transaction. Provide the card or account number as well.")
33
 
34
  class AgentState(TypedDict):
@@ -38,8 +43,8 @@ class Agent:
38
  def __init__(self, model, system=""):
39
  self.system = system
40
  graph = StateGraph(AgentState)
41
- graph.add_node("classify_txn_type", self.classify_txn_type, retry=RetryPolicy(retry_on=[groq.BadRequestError], max_attempts=2))
42
- graph.add_node("parse_message", self.parse_message, retry=RetryPolicy(retry_on=[groq.BadRequestError], max_attempts=2))
43
  graph.add_node("write_message", self.write_message)
44
  graph.add_conditional_edges(
45
  "classify_txn_type",
@@ -53,17 +58,17 @@ class Agent:
53
  self.model = model
54
 
55
  def classify_txn_type(self, state: AgentState) -> AgentState:
56
- print("Classifying transaction type...")
57
  messages = state["messages"]
58
  if self.system:
59
  messages = [SystemMessage(content=self.system)] + messages
60
 
61
  message = self.model.invoke(messages)
62
- print("Classifying transaction type completed.")
63
  return {"messages": [message]}
64
 
65
  def parse_message(self, state: AgentState) -> AgentState:
66
- print("Parsing transaction message...")
67
  message = state["messages"][0]#.content
68
  system = """
69
  You are a helpful assistant skilled at parsing transaction messages and providing structured responses.
@@ -73,17 +78,18 @@ class Agent:
73
  prompt = ChatPromptTemplate.from_messages([("system", system), ("human", human)])
74
  chain = prompt | self.model.with_structured_output(TransactionParser)
75
  result = chain.invoke({"topic": message})
76
- print("Parsing transaction message completed.")
77
  return {"messages": [result]}
78
 
79
  def write_message(self, state: AgentState) -> AgentState:
80
- print("Writing transaction message to Google Sheets...")
81
  result = state["messages"][-1]
82
  SCOPES = ('https://www.googleapis.com/auth/spreadsheets', 'https://www.googleapis.com/auth/drive')
 
83
  service_account_info = json.loads(GOOGLESHEETS_CREDENTIALS)
84
- my_credentials = service_account.Credentials.from_service_account_info(service_account_info, scopes=SCOPES)
85
- client = pygsheets.authorize(custom_credentials=my_credentials)
86
- worksheet = client.open_by_url(sheet_url)
87
  wk = worksheet[0]
88
  # Get number of rows in the worksheet
89
  df = wk.get_as_df(start='A1', end='G999')
@@ -95,7 +101,7 @@ class Agent:
95
  wk.update_value(f'E{nrows+2}', result.transaction_date)
96
  wk.update_value(f'F{nrows+2}', result.transaction_origin)
97
  wk.update_value(f'G{nrows+2}', state["messages"][0])
98
- print("Writing transaction message to Google Sheets completed.")
99
  return {"messages": ["Transaction Completed"]}
100
 
101
  def check_txn_and_decide(self, state: AgentState):
@@ -109,7 +115,8 @@ class Agent:
109
  prompt = """You are a smart assistant adept at classifying different messages. \
110
  You will be penalized heavily for incorrect classification. \
111
  Your task is to classify the message into one of the following categories: \
112
- Transaction, OTP, Promotional, Scheduled. \
 
113
  Output the classification in a structured format like below. \
114
  {"classification": "OTP"} \
115
  """
 
15
  import os
16
  from langchain_groq import ChatGroq
17
  import groq
18
+ from datetime import datetime
19
 
20
+ # Load environment variables
21
+ from dotenv import load_dotenv
22
+ load_dotenv()
23
+
24
+ SHEET_URL = os.getenv("SHEET_URL")
25
  GOOGLESHEETS_CREDENTIALS = os.getenv("GOOGLESHEETS_CREDENTIALS")
26
  GROQ_API_KEY = os.environ.get("GROQ_API_KEY")
27
  MODEL = "meta-llama/llama-4-scout-17b-16e-instruct"
 
29
  class TransactionParser(BaseModel):
30
  """This Pydantic class is used to parse the transaction message."""
31
 
32
+ amount: str = Field(description="The amount of the transaction strictly in decimal format. Do not insert currency symbol.", example="123.45")
33
  dr_or_cr: str = Field(description="Identify if the transaction was debit (spent) or credit (received). Strictly choose one of the values - Debit or Credit")
34
+ receiver: str = Field(description="The recipient of the transaction. Identify the Merchant Name from the message text.")
35
  category: str = Field(description="The category of the transaction. The category of the transaction is linked to the Merchant Name. Strictly choose from one the of values - Shopping,EMI,Education,Miscellaneous,Grocery,Utility,House Help,Travel,Transport")
36
+ transaction_date: str = Field(description="Use current system date strictly in yyyy-mm-dd format.")
37
  transaction_origin: str = Field(description="The origin of the transaction. Provide the card or account number as well.")
38
 
39
  class AgentState(TypedDict):
 
43
  def __init__(self, model, system=""):
44
  self.system = system
45
  graph = StateGraph(AgentState)
46
+ graph.add_node("classify_txn_type", self.classify_txn_type, retry=RetryPolicy(retry_on=[groq.APIConnectionError], max_attempts=5))
47
+ graph.add_node("parse_message", self.parse_message, retry=RetryPolicy(retry_on=[groq.APIConnectionError], max_attempts=5))
48
  graph.add_node("write_message", self.write_message)
49
  graph.add_conditional_edges(
50
  "classify_txn_type",
 
58
  self.model = model
59
 
60
  def classify_txn_type(self, state: AgentState) -> AgentState:
61
+ print(f"{datetime.now()}: Classifying transaction type...")
62
  messages = state["messages"]
63
  if self.system:
64
  messages = [SystemMessage(content=self.system)] + messages
65
 
66
  message = self.model.invoke(messages)
67
+ print(f"{datetime.now()}: Classifying transaction type completed.")
68
  return {"messages": [message]}
69
 
70
  def parse_message(self, state: AgentState) -> AgentState:
71
+ print(f"{datetime.now()}: Parsing transaction message...")
72
  message = state["messages"][0]#.content
73
  system = """
74
  You are a helpful assistant skilled at parsing transaction messages and providing structured responses.
 
78
  prompt = ChatPromptTemplate.from_messages([("system", system), ("human", human)])
79
  chain = prompt | self.model.with_structured_output(TransactionParser)
80
  result = chain.invoke({"topic": message})
81
+ print(f"{datetime.now()}: Parsing transaction message completed.")
82
  return {"messages": [result]}
83
 
84
  def write_message(self, state: AgentState) -> AgentState:
85
+ print(f"{datetime.now()}: Writing transaction message to Google Sheets...")
86
  result = state["messages"][-1]
87
  SCOPES = ('https://www.googleapis.com/auth/spreadsheets', 'https://www.googleapis.com/auth/drive')
88
+
89
  service_account_info = json.loads(GOOGLESHEETS_CREDENTIALS)
90
+ credentials = service_account.Credentials.from_service_account_info(service_account_info, scopes=SCOPES)
91
+ client = pygsheets.authorize(custom_credentials=credentials)
92
+ worksheet = client.open_by_url(SHEET_URL)
93
  wk = worksheet[0]
94
  # Get number of rows in the worksheet
95
  df = wk.get_as_df(start='A1', end='G999')
 
101
  wk.update_value(f'E{nrows+2}', result.transaction_date)
102
  wk.update_value(f'F{nrows+2}', result.transaction_origin)
103
  wk.update_value(f'G{nrows+2}', state["messages"][0])
104
+ print(f"{datetime.now()}: Writing transaction message to Google Sheets completed.")
105
  return {"messages": ["Transaction Completed"]}
106
 
107
  def check_txn_and_decide(self, state: AgentState):
 
115
  prompt = """You are a smart assistant adept at classifying different messages. \
116
  You will be penalized heavily for incorrect classification. \
117
  Your task is to classify the message into one of the following categories: \
118
+ Transaction, OTP, Promotional, Scheduled, Non-Transaction. \
119
+ Consider Salary Credit, Interest Credit, Redemtions as non-transactional messages.
120
  Output the classification in a structured format like below. \
121
  {"classification": "OTP"} \
122
  """
requirements.txt CHANGED
@@ -4,4 +4,5 @@ langchain-ollama
4
  langgraph
5
  pygsheets
6
  pandas
7
- langchain-groq
 
 
4
  langgraph
5
  pygsheets
6
  pandas
7
+ langchain-groq
8
+ dotenv