gopichandra commited on
Commit
89e89ee
·
verified ·
1 Parent(s): 5686c7d

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +57 -16
app.py CHANGED
@@ -2,6 +2,7 @@ import os
2
  os.environ["OMP_NUM_THREADS"] = "1"
3
 
4
  import re
 
5
  import datetime as dt
6
  import gradio as gr
7
  from utils import extract_kyc_fields
@@ -101,18 +102,49 @@ def sf_connect():
101
  if not SF_AVAILABLE:
102
  raise RuntimeError("simple-salesforce is not installed. Add `simple-salesforce` to requirements.txt.")
103
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
104
  try:
105
- sf = Salesforce(
106
- username=SF_USERNAME,
107
- password=SF_PASSWORD,
108
- security_token=SF_SECURITY_TOKEN,
109
- domain=SF_DOMAIN,
110
- )
111
- # quick auth sanity check
112
- sf.query("SELECT Id FROM User LIMIT 1")
113
- return sf
 
 
 
 
 
 
 
 
 
 
 
114
  except Exception as e:
115
- raise e
 
116
 
117
 
118
  def sf_push_kyc_record(sf, ocr_results):
@@ -136,25 +168,32 @@ def sf_push_kyc_record(sf, ocr_results):
136
  payload = {
137
  "Aadhaar_Number__c": aadhaar_number,
138
  "Aadhaar_Name__c": aadhaar_name,
139
- "Aadhaar_DOB__c": aadhaar_dob,
140
  "PAN_Number__c": pan_number,
141
  "Pan_Name__c": pan_name,
142
- "Pan_DOB__c": pan_dob,
143
  }
 
144
  payload = {k: v for k, v in payload.items() if v is not None}
145
 
 
146
  try:
147
  result = sf.KYC_Record__c.create(payload)
148
- return {"success": True, "id": result.get("id"), "payload": payload}
149
  except Exception as e:
150
- return {"success": False, "error": _fmt_sf_error(e), "payload": payload}
 
 
 
 
 
151
 
152
 
153
  # ---------- gradio callback ----------
154
  def process_documents(aadhaar_file, pan_file, push_to_sf):
155
  """
156
  - Runs OCR on Aadhaar and PAN separately.
157
- - Optionally pushes a single KYC_Record__c to Salesforce.
158
  """
159
  results = {"aadhaar": None, "pan": None}
160
 
@@ -187,6 +226,7 @@ def process_documents(aadhaar_file, pan_file, push_to_sf):
187
  created = sf_push_kyc_record(sf, results)
188
  output["salesforce"] = {"pushed": created.get("success", False), **created}
189
  except Exception as e:
 
190
  output["salesforce"] = {"pushed": False, "error": _fmt_sf_error(e)}
191
 
192
  return output
@@ -227,9 +267,10 @@ with gr.Blocks(title="Smart KYC OCR → Salesforce (KYC_Record__c)") as demo:
227
  gr.Markdown("---")
228
  gr.Markdown(
229
  """
230
- ⚠️ Credentials are embedded in this file. Keep this code private and rotate the token if shared.
231
  """
232
  )
233
 
 
234
  if __name__ == "__main__":
235
  demo.launch()
 
2
  os.environ["OMP_NUM_THREADS"] = "1"
3
 
4
  import re
5
+ import json
6
  import datetime as dt
7
  import gradio as gr
8
  from utils import extract_kyc_fields
 
102
  if not SF_AVAILABLE:
103
  raise RuntimeError("simple-salesforce is not installed. Add `simple-salesforce` to requirements.txt.")
104
 
105
+ sf = Salesforce(
106
+ username=SF_USERNAME,
107
+ password=SF_PASSWORD,
108
+ security_token=SF_SECURITY_TOKEN,
109
+ domain=SF_DOMAIN,
110
+ )
111
+ # quick auth sanity check (will raise on bad auth)
112
+ sf.query("SELECT Id FROM User LIMIT 1")
113
+ return sf
114
+
115
+
116
+ def _raw_create_with_fallback(sf, object_api_name: str, payload: dict):
117
+ """
118
+ Fallback path that bypasses simple-salesforce's error wrappers and calls REST directly.
119
+ Always returns a dict:
120
+ - on success: {"success": True, "id": "...", "url": "...", "status_code": 201}
121
+ - on error: {"success": False, "status_code": <int>, "url": "...", "response_json": <json or None>, "response_text": <str>}
122
+ """
123
+ url = f"{sf.base_url}sobjects/{object_api_name}"
124
  try:
125
+ resp = sf.session.post(url, json=payload, headers=sf.headers, timeout=30)
126
+ status = resp.status_code
127
+ try:
128
+ body = resp.json()
129
+ except Exception:
130
+ body = None
131
+
132
+ if 200 <= status < 300:
133
+ # Salesforce returns {"id": "...", "success": true, "errors": []}
134
+ rec_id = (body or {}).get("id") if isinstance(body, dict) else None
135
+ return {"success": True, "id": rec_id, "status_code": status, "url": url, "response_json": body}
136
+ else:
137
+ # Return raw details so you see the exact field/object error
138
+ return {
139
+ "success": False,
140
+ "status_code": status,
141
+ "url": url,
142
+ "response_json": body,
143
+ "response_text": resp.text,
144
+ }
145
  except Exception as e:
146
+ # Network or session issues
147
+ return {"success": False, "url": url, "exception": _fmt_sf_error(e)}
148
 
149
 
150
  def sf_push_kyc_record(sf, ocr_results):
 
168
  payload = {
169
  "Aadhaar_Number__c": aadhaar_number,
170
  "Aadhaar_Name__c": aadhaar_name,
171
+ "Aadhaar_DOB__c": aadhaar_dob, # Date field in SF
172
  "PAN_Number__c": pan_number,
173
  "Pan_Name__c": pan_name,
174
+ "Pan_DOB__c": pan_dob, # Date field in SF
175
  }
176
+ # Remove None keys to avoid nulling non-nullable fields
177
  payload = {k: v for k, v in payload.items() if v is not None}
178
 
179
+ # First try the nice SDK method
180
  try:
181
  result = sf.KYC_Record__c.create(payload)
182
+ return {"success": True, "id": result.get("id"), "payload": payload, "via": "sdk"}
183
  except Exception as e:
184
+ # If simple-salesforce throws its unhelpful TypeError, fall back to a raw REST POST
185
+ raw = _raw_create_with_fallback(sf, "KYC_Record__c", payload)
186
+ if raw.get("success"):
187
+ return {"success": True, "id": raw.get("id"), "payload": payload, "via": "raw", "raw": raw}
188
+ else:
189
+ return {"success": False, "error": _fmt_sf_error(e), "payload": payload, "raw": raw}
190
 
191
 
192
  # ---------- gradio callback ----------
193
  def process_documents(aadhaar_file, pan_file, push_to_sf):
194
  """
195
  - Runs OCR on Aadhaar and PAN separately.
196
+ - Optionally pushes a single KYC_Record__c to Salesforce with robust fallback.
197
  """
198
  results = {"aadhaar": None, "pan": None}
199
 
 
226
  created = sf_push_kyc_record(sf, results)
227
  output["salesforce"] = {"pushed": created.get("success", False), **created}
228
  except Exception as e:
229
+ # Even connection/auth errors will be formatted
230
  output["salesforce"] = {"pushed": False, "error": _fmt_sf_error(e)}
231
 
232
  return output
 
267
  gr.Markdown("---")
268
  gr.Markdown(
269
  """
270
+ If an error occurs, you'll now see **status_code**, **url**, and Salesforce’s **response_json** for fast debugging.
271
  """
272
  )
273
 
274
+ # Important for Spaces: keep `demo` at module level
275
  if __name__ == "__main__":
276
  demo.launch()