Yaswanth56 commited on
Commit
f87cd2d
·
verified ·
1 Parent(s): f32706c

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +11 -86
app.py CHANGED
@@ -11,7 +11,6 @@ from simple_salesforce import Salesforce
11
  import os
12
  from dotenv import load_dotenv
13
  import base64
14
- import io
15
  import concurrent.futures
16
 
17
  # Load environment variables from .env file
@@ -36,34 +35,24 @@ model.eval()
36
  device = "cuda" if torch.cuda.is_available() else "cpu"
37
  model.to(device)
38
 
39
- # Inference function to generate captions dynamically based on image content
40
  def generate_captions_from_image(image):
41
  if image.mode != "RGB":
42
  image = image.convert("RGB")
43
-
44
- # Resize image for faster processing (use smaller resolution to speed up inference)
45
- image = image.resize((320, 320)) # Reduced size for faster processing
46
-
47
- # Preprocess the image and generate a caption
48
  inputs = processor(image, return_tensors="pt").to(device, torch.float16)
49
  output = model.generate(**inputs, max_new_tokens=50)
50
  caption = processor.decode(output[0], skip_special_tokens=True)
51
-
52
  return caption
53
 
54
- # Function to save DPR text to a PDF file
55
  def save_dpr_to_pdf(dpr_text, image_paths, captions, filename):
56
  try:
57
- # Create a PDF document
58
  doc = SimpleDocTemplate(filename, pagesize=letter)
59
  styles = getSampleStyleSheet()
60
-
61
- # Define custom styles
62
  title_style = ParagraphStyle(
63
  name='Title',
64
  fontSize=16,
65
  leading=20,
66
- alignment=1, # Center
67
  spaceAfter=20,
68
  textColor=colors.black,
69
  fontName='Helvetica-Bold'
@@ -76,179 +65,117 @@ def save_dpr_to_pdf(dpr_text, image_paths, captions, filename):
76
  textColor=colors.black,
77
  fontName='Helvetica'
78
  )
79
-
80
- # Build the PDF content
81
  flowables = []
82
-
83
- # Add title
84
  flowables.append(Paragraph("Daily Progress Report", title_style))
85
-
86
- # Split DPR text into lines and add as paragraphs (excluding descriptions for images)
87
  for line in dpr_text.split('\n'):
88
- # Replace problematic characters for PDF
89
  line = line.replace('\u2019', "'").replace('\u2018', "'")
90
  if line.strip():
91
  flowables.append(Paragraph(line, body_style))
92
  else:
93
  flowables.append(Spacer(1, 12))
94
-
95
- # Add images and captions in the correct order (no need to add description to dpr_text again)
96
  for img_path, caption in zip(image_paths, captions):
97
  try:
98
- # Add image first
99
- img = PDFImage(img_path, width=200, height=150) # Adjust image size if needed
100
  flowables.append(img)
101
- # Add description below the image
102
  description = f"Description: {caption}"
103
  flowables.append(Paragraph(description, body_style))
104
- flowables.append(Spacer(1, 12)) # Add some space between images
105
  except Exception as e:
106
  flowables.append(Paragraph(f"Error loading image: {str(e)}", body_style))
107
-
108
- # Build the PDF
109
  doc.build(flowables)
110
  return f"PDF saved successfully as {filename}", filename
111
  except Exception as e:
112
  return f"Error saving PDF: {str(e)}", None
113
 
114
- # Function to upload a file to Salesforce as ContentVersion
115
  def upload_file_to_salesforce(file_path, filename, sf_connection, file_type):
116
  try:
117
- # Read file content and encode in base64
118
  with open(file_path, 'rb') as f:
119
  file_content = f.read()
120
  file_content_b64 = base64.b64encode(file_content).decode('utf-8')
121
-
122
- # Set description based on file type
123
  description = "Daily Progress Report PDF" if file_type == "pdf" else "Site Image"
124
-
125
- # Create ContentVersion
126
  content_version = sf_connection.ContentVersion.create({
127
  'Title': filename,
128
  'PathOnClient': filename,
129
  'VersionData': file_content_b64,
130
  'Description': description
131
  })
132
-
133
- # Get ContentDocumentId
134
  content_version_id = content_version['id']
135
  content_document = sf_connection.query(
136
  f"SELECT ContentDocumentId FROM ContentVersion WHERE Id = '{content_version_id}'"
137
  )
138
  content_document_id = content_document['records'][0]['ContentDocumentId']
139
-
140
- # Generate a valid Salesforce URL for the ContentDocument
141
  content_document_url = f"https://{sf_connection.sf_instance}/sfc/servlet.shepherd/version/download/{content_version_id}"
142
-
143
- # Ensure the link is valid
144
  return content_document_id, content_document_url, f"File {filename} uploaded successfully"
145
  except Exception as e:
146
  return None, None, f"Error uploading {filename} to Salesforce: {str(e)}"
147
 
148
- # Function to generate the daily progress report (DPR), save as PDF, and upload to Salesforce
149
  def generate_dpr(files):
150
  dpr_text = []
151
  captions = []
152
  image_paths = []
153
  current_time = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
154
-
155
- # Add header to the DPR
156
  dpr_text.append(f"Daily Progress Report\nGenerated on: {current_time}\n")
157
-
158
- # Process images in parallel for faster performance
159
  with concurrent.futures.ThreadPoolExecutor() as executor:
160
  results = list(executor.map(lambda file: generate_captions_from_image(Image.open(file.name)), files))
161
-
162
  for i, file in enumerate(files):
163
  caption = results[i]
164
  captions.append(caption)
165
-
166
- # Generate DPR section for this image with dynamic caption
167
  dpr_section = f"\nImage: {file.name}\nDescription: {caption}\n"
168
  dpr_text.append(dpr_section)
169
-
170
- # Save image path for embedding in the report
171
  image_paths.append(file.name)
172
-
173
- # Combine DPR text
174
  dpr_output = "\n".join(dpr_text)
175
-
176
- # Generate PDF filename with timestamp
177
  pdf_filename = f"DPR_{datetime.now().strftime('%Y-%m-%d_%H-%M-%S')}.pdf"
178
-
179
- # Save DPR text to PDF
180
  pdf_result, pdf_filepath = save_dpr_to_pdf(dpr_output, image_paths, captions, pdf_filename)
181
-
182
  salesforce_result = ""
183
  pdf_content_document_id = None
184
  pdf_url = None
185
- image_content_document_ids = []
186
-
187
  if sf and pdf_filepath:
188
  try:
189
- # Create Daily_Progress_Reports__c record
190
- report_description = "; ".join(captions)[:255] # Concatenate captions, limit to 255 chars
191
  dpr_record = sf.Daily_Progress_Reports__c.create({
192
- 'Detected_Activities__c': report_description # Store in Detected_Activities__c field
193
  })
194
  dpr_record_id = dpr_record['id']
195
  salesforce_result += f"Created Daily_Progress_Reports__c record with ID: {dpr_record_id}\n"
196
-
197
- # Upload PDF to Salesforce
198
  pdf_content_document_id, pdf_url, pdf_upload_result = upload_file_to_salesforce(
199
  pdf_filepath, pdf_filename, sf, "pdf"
200
  )
201
  salesforce_result += pdf_upload_result + "\n"
202
-
203
- # Link PDF to DPR record
204
  if pdf_content_document_id:
205
  sf.ContentDocumentLink.create({
206
  'ContentDocumentId': pdf_content_document_id,
207
  'LinkedEntityId': dpr_record_id,
208
  'ShareType': 'V'
209
  })
210
-
211
- # Update the DPR record with the PDF URL
212
  if pdf_url:
213
  sf.Daily_Progress_Reports__c.update(dpr_record_id, {
214
- 'PDF_URL__c': pdf_url # Storing the PDF URL correctly
215
  })
216
  salesforce_result += f"Updated PDF URL for record ID {dpr_record_id}\n"
217
-
218
- # Upload images to Salesforce and link them to DPR record
219
  for file in files:
220
  image_filename = os.path.basename(file.name)
221
  image_content_document_id, image_url, image_upload_result = upload_file_to_salesforce(
222
  file.name, image_filename, sf, "image"
223
  )
224
-
225
  if image_content_document_id:
226
- # Link image to the Daily Progress Report record (DPR) using ContentDocumentLink
227
  sf.ContentDocumentLink.create({
228
  'ContentDocumentId': image_content_document_id,
229
- 'LinkedEntityId': dpr_record_id, # Link image to DPR record
230
- 'ShareType': 'V' # 'V' means Viewer access
231
  })
232
-
233
- # Now, update the DPR record with the ContentDocumentId in the Site_Images field (if it's a text or URL field)
234
  sf.Daily_Progress_Reports__c.update(dpr_record_id, {
235
- 'Site_Images__c': image_content_document_id # Storing the ContentDocumentId directly
236
  })
237
-
238
  salesforce_result += image_upload_result + "\n"
239
-
240
  except Exception as e:
241
  salesforce_result += f"Error interacting with Salesforce: {str(e)}\n"
242
  else:
243
  salesforce_result = "Salesforce connection not available or PDF generation failed.\n"
244
-
245
- # Return DPR text, PDF file, and Salesforce upload status
246
  return (
247
  dpr_output + f"\n\n{pdf_result}\n\nSalesforce Upload Status:\n{salesforce_result}",
248
  pdf_filepath
249
  )
250
 
251
- # Gradio interface for uploading multiple files, displaying DPR, and downloading PDF
252
  iface = gr.Interface(
253
  fn=generate_dpr,
254
  inputs=gr.Files(type="filepath", label="Upload Site Photos"),
@@ -258,9 +185,7 @@ iface = gr.Interface(
258
  ],
259
  title="Daily Progress Report Generator",
260
  description="Upload up to 10 site photos. The AI model will generate a text-based Daily Progress Report (DPR), save it as a PDF, and upload the PDF and images to Salesforce under Daily_Progress_Reports__c in the Files related list. Download the PDF locally if needed.",
261
- allow_flagging="never",
262
- show_api=False,
263
- show_tips=False
264
  )
265
 
266
  if __name__ == "__main__":
 
11
  import os
12
  from dotenv import load_dotenv
13
  import base64
 
14
  import concurrent.futures
15
 
16
  # Load environment variables from .env file
 
35
  device = "cuda" if torch.cuda.is_available() else "cpu"
36
  model.to(device)
37
 
 
38
  def generate_captions_from_image(image):
39
  if image.mode != "RGB":
40
  image = image.convert("RGB")
41
+ image = image.resize((320, 320))
 
 
 
 
42
  inputs = processor(image, return_tensors="pt").to(device, torch.float16)
43
  output = model.generate(**inputs, max_new_tokens=50)
44
  caption = processor.decode(output[0], skip_special_tokens=True)
 
45
  return caption
46
 
 
47
  def save_dpr_to_pdf(dpr_text, image_paths, captions, filename):
48
  try:
 
49
  doc = SimpleDocTemplate(filename, pagesize=letter)
50
  styles = getSampleStyleSheet()
 
 
51
  title_style = ParagraphStyle(
52
  name='Title',
53
  fontSize=16,
54
  leading=20,
55
+ alignment=1,
56
  spaceAfter=20,
57
  textColor=colors.black,
58
  fontName='Helvetica-Bold'
 
65
  textColor=colors.black,
66
  fontName='Helvetica'
67
  )
 
 
68
  flowables = []
 
 
69
  flowables.append(Paragraph("Daily Progress Report", title_style))
 
 
70
  for line in dpr_text.split('\n'):
 
71
  line = line.replace('\u2019', "'").replace('\u2018', "'")
72
  if line.strip():
73
  flowables.append(Paragraph(line, body_style))
74
  else:
75
  flowables.append(Spacer(1, 12))
 
 
76
  for img_path, caption in zip(image_paths, captions):
77
  try:
78
+ img = PDFImage(img_path, width=200, height=150)
 
79
  flowables.append(img)
 
80
  description = f"Description: {caption}"
81
  flowables.append(Paragraph(description, body_style))
82
+ flowables.append(Spacer(1, 12))
83
  except Exception as e:
84
  flowables.append(Paragraph(f"Error loading image: {str(e)}", body_style))
 
 
85
  doc.build(flowables)
86
  return f"PDF saved successfully as {filename}", filename
87
  except Exception as e:
88
  return f"Error saving PDF: {str(e)}", None
89
 
 
90
  def upload_file_to_salesforce(file_path, filename, sf_connection, file_type):
91
  try:
 
92
  with open(file_path, 'rb') as f:
93
  file_content = f.read()
94
  file_content_b64 = base64.b64encode(file_content).decode('utf-8')
 
 
95
  description = "Daily Progress Report PDF" if file_type == "pdf" else "Site Image"
 
 
96
  content_version = sf_connection.ContentVersion.create({
97
  'Title': filename,
98
  'PathOnClient': filename,
99
  'VersionData': file_content_b64,
100
  'Description': description
101
  })
 
 
102
  content_version_id = content_version['id']
103
  content_document = sf_connection.query(
104
  f"SELECT ContentDocumentId FROM ContentVersion WHERE Id = '{content_version_id}'"
105
  )
106
  content_document_id = content_document['records'][0]['ContentDocumentId']
 
 
107
  content_document_url = f"https://{sf_connection.sf_instance}/sfc/servlet.shepherd/version/download/{content_version_id}"
 
 
108
  return content_document_id, content_document_url, f"File {filename} uploaded successfully"
109
  except Exception as e:
110
  return None, None, f"Error uploading {filename} to Salesforce: {str(e)}"
111
 
 
112
  def generate_dpr(files):
113
  dpr_text = []
114
  captions = []
115
  image_paths = []
116
  current_time = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
 
 
117
  dpr_text.append(f"Daily Progress Report\nGenerated on: {current_time}\n")
 
 
118
  with concurrent.futures.ThreadPoolExecutor() as executor:
119
  results = list(executor.map(lambda file: generate_captions_from_image(Image.open(file.name)), files))
 
120
  for i, file in enumerate(files):
121
  caption = results[i]
122
  captions.append(caption)
 
 
123
  dpr_section = f"\nImage: {file.name}\nDescription: {caption}\n"
124
  dpr_text.append(dpr_section)
 
 
125
  image_paths.append(file.name)
 
 
126
  dpr_output = "\n".join(dpr_text)
 
 
127
  pdf_filename = f"DPR_{datetime.now().strftime('%Y-%m-%d_%H-%M-%S')}.pdf"
 
 
128
  pdf_result, pdf_filepath = save_dpr_to_pdf(dpr_output, image_paths, captions, pdf_filename)
 
129
  salesforce_result = ""
130
  pdf_content_document_id = None
131
  pdf_url = None
 
 
132
  if sf and pdf_filepath:
133
  try:
134
+ report_description = "; ".join(captions)[:255]
 
135
  dpr_record = sf.Daily_Progress_Reports__c.create({
136
+ 'Detected_Activities__c': report_description
137
  })
138
  dpr_record_id = dpr_record['id']
139
  salesforce_result += f"Created Daily_Progress_Reports__c record with ID: {dpr_record_id}\n"
 
 
140
  pdf_content_document_id, pdf_url, pdf_upload_result = upload_file_to_salesforce(
141
  pdf_filepath, pdf_filename, sf, "pdf"
142
  )
143
  salesforce_result += pdf_upload_result + "\n"
 
 
144
  if pdf_content_document_id:
145
  sf.ContentDocumentLink.create({
146
  'ContentDocumentId': pdf_content_document_id,
147
  'LinkedEntityId': dpr_record_id,
148
  'ShareType': 'V'
149
  })
 
 
150
  if pdf_url:
151
  sf.Daily_Progress_Reports__c.update(dpr_record_id, {
152
+ 'PDF_URL__c': pdf_url
153
  })
154
  salesforce_result += f"Updated PDF URL for record ID {dpr_record_id}\n"
 
 
155
  for file in files:
156
  image_filename = os.path.basename(file.name)
157
  image_content_document_id, image_url, image_upload_result = upload_file_to_salesforce(
158
  file.name, image_filename, sf, "image"
159
  )
 
160
  if image_content_document_id:
 
161
  sf.ContentDocumentLink.create({
162
  'ContentDocumentId': image_content_document_id,
163
+ 'LinkedEntityId': dpr_record_id,
164
+ 'ShareType': 'V'
165
  })
 
 
166
  sf.Daily_Progress_Reports__c.update(dpr_record_id, {
167
+ 'Site_Images__c': image_content_document_id
168
  })
 
169
  salesforce_result += image_upload_result + "\n"
 
170
  except Exception as e:
171
  salesforce_result += f"Error interacting with Salesforce: {str(e)}\n"
172
  else:
173
  salesforce_result = "Salesforce connection not available or PDF generation failed.\n"
 
 
174
  return (
175
  dpr_output + f"\n\n{pdf_result}\n\nSalesforce Upload Status:\n{salesforce_result}",
176
  pdf_filepath
177
  )
178
 
 
179
  iface = gr.Interface(
180
  fn=generate_dpr,
181
  inputs=gr.Files(type="filepath", label="Upload Site Photos"),
 
185
  ],
186
  title="Daily Progress Report Generator",
187
  description="Upload up to 10 site photos. The AI model will generate a text-based Daily Progress Report (DPR), save it as a PDF, and upload the PDF and images to Salesforce under Daily_Progress_Reports__c in the Files related list. Download the PDF locally if needed.",
188
+ allow_flagging="never"
 
 
189
  )
190
 
191
  if __name__ == "__main__":