ak0601 commited on
Commit
ba9e19c
·
verified ·
1 Parent(s): ee11810

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +42 -37
app.py CHANGED
@@ -1,4 +1,4 @@
1
-
2
  import os
3
  import json
4
  from dotenv import load_dotenv
@@ -14,25 +14,16 @@ from google.adk.runners import Runner
14
  from google.adk.tools import FunctionTool
15
  from google.genai import types
16
  from langchain_tavily import TavilySearch
17
- import gspread
18
  import uuid
19
  import datetime
20
 
21
  # === CONFIGURE ENV AND AUTH ===
22
  load_dotenv()
23
- hf_token = os.getenv("HUGGINGFACE_TOKEN")
24
- assert hf_token, "Please set HUGGINGFACE_TOKEN in your .env"
25
- login(token=hf_token)
26
- assert os.getenv("GOOGLE_API_KEY"), "Set GOOGLE_API_KEY in .env"
27
- assert os.getenv("TAVILY_API_KEY"), "Set TAVILY_API_KEY in .env"
28
- genai.configure(api_key=os.getenv("GOOGLE_API_KEY"))
29
-
30
-
31
  service_account_path = {
32
  "type": os.getenv("type"),
33
  "project_id": os.getenv("project_id"),
34
  "private_key_id": str(os.getenv("private_key_id")).replace('\\n', '\n'),
35
- "private_key": str(os.getenv("private_key")).replace('\\n', '\n'),
36
  "client_email": os.getenv("client_email"),
37
  "client_id": os.getenv("client_id"),
38
  "auth_uri": os.getenv("auth_uri"),
@@ -41,17 +32,12 @@ service_account_path = {
41
  "client_x509_cert_url": os.getenv("client_x509_cert_url"),
42
  "universe_domain":os.getenv("universe_domain")
43
  }
44
-
45
- def add_query_to_sheet(user_id, query, response):
46
- gc = gspread.service_account_from_dict(service_account_path)
47
- sh = gc.open_by_key(SHEET_KEY)
48
- worksheet = sh.worksheet("Sheet1")
49
-
50
-
51
- timestamp = datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
52
- worksheet.append_row([user_id, timestamp, query, response])
53
-
54
-
55
 
56
  def flatten_json(obj: dict) -> str:
57
  pieces = []
@@ -63,6 +49,8 @@ def flatten_json(obj: dict) -> str:
63
  recurse("", obj)
64
  return "\n".join(pieces)
65
 
 
 
66
  # === LOAD AND INDEX LOCAL COLLEGE JSONS ===
67
  @st.cache_resource
68
  def load_vector_store(data_dir: str):
@@ -71,10 +59,12 @@ def load_vector_store(data_dir: str):
71
  if fname.lower().endswith('.json'):
72
  path = os.path.join(data_dir, fname)
73
  try:
74
- with open(path, 'r', encoding='utf-8') as f: data = json.load(f)
 
75
  except UnicodeDecodeError:
76
- with open(path, 'r', encoding='latin-1') as f: data = json.load(f)
77
- texts.append(flatten_json(data))
 
78
  # st.info(f"Loaded {len(texts)} documents.")
79
 
80
  st_model = SentenceTransformer('all-MiniLM-L6-v2')
@@ -84,8 +74,22 @@ def load_vector_store(data_dir: str):
84
 
85
  return FAISS.from_texts(texts, LocalEmbeddings())
86
 
87
- vector_store = load_vector_store('Jsons-Colleges/Jsons')
 
 
 
88
 
 
 
 
 
 
 
 
 
 
 
 
89
  # === TOOLS ===
90
  def db_search(query: str) -> dict:
91
  docs = vector_store.similarity_search(query, k=6)
@@ -107,7 +111,7 @@ tavily_tool = FunctionTool(tavily_search)
107
 
108
  # === AGENT SETUP ===
109
  @st.cache_resource
110
- def create_agent():
111
  agent = Agent(
112
  name="college_info_agent",
113
  model="gemini-2.0-flash",
@@ -118,7 +122,8 @@ You are a highly experienced college counselor, specializing in helping high sch
118
  2. If `db_search` returns an empty `results` list, immediately call `tavily_search`.\n
119
  3. Do not produce any output until one of those calls returns data.\n
120
  4. As soon as you have non‑empty results, stop further searches and craft your answer using only that source.\n
121
- 5. When suggesting a list of colleges based on student's rank, always consider the following:
 
122
  a. Rank of the student (mandatory)
123
  b. Category (if not provided, assume General)
124
  c. State (optional)
@@ -126,16 +131,17 @@ You are a highly experienced college counselor, specializing in helping high sch
126
 
127
  Note: In your final response, only include colleges where the student is eligible based on their rank. Do not list colleges where the cutoff rank is lower than the student's rank. Ask them to check out Precollege Predictor for more personalized answers, the link of college predictor https://www.precollege.in/college-predictor
128
 
129
- 6. Rank Eligibility Rule: A student is eligible for a college if their rank is less than or equal to the college’s closing cutoff. (e.g., Rank 2000 is eligible if the cutoff is 2500.)
130
 
131
- 7. If the user wants to compare colleges, present the comparison in a table format for clarity (Mention the opening and closing ranks for the General category.).
 
 
132
 
133
- 8. If you cannot find sufficient or specific information, politely direct the student to connect with a verified mentor at: https://precollege.in
134
 
135
- 9. If the user asks a question unrelated to college counseling, respond with:
136
  "Sorry, this is beyond the scope of this application"
137
  """
138
-
139
  ),
140
  tools=[db_tool, tavily_tool],
141
  generate_content_config=types.GenerateContentConfig(
@@ -144,11 +150,11 @@ You are a highly experienced college counselor, specializing in helping high sch
144
  )
145
  )
146
  session_svc = InMemorySessionService()
147
- session = session_svc.create_session(app_name="college_agent_app", user_id="user1", session_id="session1")
148
  runner = Runner(agent=agent, app_name="college_agent_app", session_service=session_svc)
149
  return runner, session
150
 
151
- runner, session = create_agent()
152
 
153
  # === STREAMLIT UI ===
154
  st.title("🎓 Jossa-ChatBot")
@@ -185,5 +191,4 @@ if query:
185
  reply="Please provide complete context."
186
  st.session_state.history.append(("assistant", reply))
187
  add_query_to_sheet(user_id=user_id, query=query, response=reply)
188
- st.rerun()
189
-
 
1
+ import gspread
2
  import os
3
  import json
4
  from dotenv import load_dotenv
 
14
  from google.adk.tools import FunctionTool
15
  from google.genai import types
16
  from langchain_tavily import TavilySearch
 
17
  import uuid
18
  import datetime
19
 
20
  # === CONFIGURE ENV AND AUTH ===
21
  load_dotenv()
 
 
 
 
 
 
 
 
22
  service_account_path = {
23
  "type": os.getenv("type"),
24
  "project_id": os.getenv("project_id"),
25
  "private_key_id": str(os.getenv("private_key_id")).replace('\\n', '\n'),
26
+ "private_key": str(os.getenv("private_key")).replace('\\n', '\n'),
27
  "client_email": os.getenv("client_email"),
28
  "client_id": os.getenv("client_id"),
29
  "auth_uri": os.getenv("auth_uri"),
 
32
  "client_x509_cert_url": os.getenv("client_x509_cert_url"),
33
  "universe_domain":os.getenv("universe_domain")
34
  }
35
+ hf_token = os.getenv("HUGGINGFACE_TOKEN")
36
+ assert hf_token, "Please set HUGGINGFACE_TOKEN in your .env"
37
+ login(token=hf_token)
38
+ assert os.getenv("GOOGLE_API_KEY"), "Set GOOGLE_API_KEY in .env"
39
+ assert os.getenv("TAVILY_API_KEY"), "Set TAVILY_API_KEY in .env"
40
+ genai.configure(api_key=os.getenv("GOOGLE_API_KEY"))
 
 
 
 
 
41
 
42
  def flatten_json(obj: dict) -> str:
43
  pieces = []
 
49
  recurse("", obj)
50
  return "\n".join(pieces)
51
 
52
+
53
+
54
  # === LOAD AND INDEX LOCAL COLLEGE JSONS ===
55
  @st.cache_resource
56
  def load_vector_store(data_dir: str):
 
59
  if fname.lower().endswith('.json'):
60
  path = os.path.join(data_dir, fname)
61
  try:
62
+ with open(path, 'r', encoding='utf-8') as f:
63
+ data = f.read()
64
  except UnicodeDecodeError:
65
+ with open(path, 'r', encoding='latin-1') as f:
66
+ data = f.read()
67
+ texts.append(data)
68
  # st.info(f"Loaded {len(texts)} documents.")
69
 
70
  st_model = SentenceTransformer('all-MiniLM-L6-v2')
 
74
 
75
  return FAISS.from_texts(texts, LocalEmbeddings())
76
 
77
+ vector_store = load_vector_store("Jsons-Colleges/Jsons")
78
+
79
+
80
+ SHEET_KEY = os.getenv("SHEET_KEY")
81
 
82
+ def add_query_to_sheet(user_id, query, response):
83
+ gc = gspread.service_account_from_dict(service_account_path)
84
+ sh = gc.open_by_key(SHEET_KEY)
85
+ worksheet = sh.worksheet("Sheet1")
86
+
87
+
88
+ timestamp = datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
89
+ worksheet.append_row([user_id, timestamp, query, response])
90
+
91
+
92
+
93
  # === TOOLS ===
94
  def db_search(query: str) -> dict:
95
  docs = vector_store.similarity_search(query, k=6)
 
111
 
112
  # === AGENT SETUP ===
113
  @st.cache_resource
114
+ def create_agent(user_id, session_id):
115
  agent = Agent(
116
  name="college_info_agent",
117
  model="gemini-2.0-flash",
 
122
  2. If `db_search` returns an empty `results` list, immediately call `tavily_search`.\n
123
  3. Do not produce any output until one of those calls returns data.\n
124
  4. As soon as you have non‑empty results, stop further searches and craft your answer using only that source.\n
125
+ 5. If a user asks about a college, use the available source to provide the most detailed response possible, preferably structured in bullet points for clarity.
126
+ 6. If a user enters a rank and asks a list of colleges based on their's rank, always consider the following:
127
  a. Rank of the student (mandatory)
128
  b. Category (if not provided, assume General)
129
  c. State (optional)
 
131
 
132
  Note: In your final response, only include colleges where the student is eligible based on their rank. Do not list colleges where the cutoff rank is lower than the student's rank. Ask them to check out Precollege Predictor for more personalized answers, the link of college predictor https://www.precollege.in/college-predictor
133
 
134
+ 7. Rank Eligibility Rule: A student is eligible for a college if their rank is less than or equal to the college’s closing cutoff. (e.g., Rank 2000 is eligible if the cutoff is 2500.)
135
 
136
+ 8. If the user wants to compare colleges, present the comparison in a table format for clarity (Mention the opening and closing ranks for the General category.).
137
+
138
+ 9. Ensure that your response is always complete and fully addresses the user's question, without leaving any sentence or thought unfinished.
139
 
140
+ 10. If you cannot find sufficient or specific information, politely direct the student to connect with a verified mentor at: https://precollege.in
141
 
142
+ 11. If the user asks a question unrelated to college counseling, respond with:
143
  "Sorry, this is beyond the scope of this application"
144
  """
 
145
  ),
146
  tools=[db_tool, tavily_tool],
147
  generate_content_config=types.GenerateContentConfig(
 
150
  )
151
  )
152
  session_svc = InMemorySessionService()
153
+ session = session_svc.create_session(app_name="college_agent_app",user_id=user_id, session_id=session_id)
154
  runner = Runner(agent=agent, app_name="college_agent_app", session_service=session_svc)
155
  return runner, session
156
 
157
+
158
 
159
  # === STREAMLIT UI ===
160
  st.title("🎓 Jossa-ChatBot")
 
191
  reply="Please provide complete context."
192
  st.session_state.history.append(("assistant", reply))
193
  add_query_to_sheet(user_id=user_id, query=query, response=reply)
194
+ st.rerun()