awacke1 commited on
Commit
cf22379
·
verified ·
1 Parent(s): 23a1c52

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +205 -15
app.py CHANGED
@@ -7,6 +7,8 @@ import glob
7
  import io
8
  import json
9
  import logging
 
 
10
  import os
11
  import pandas as pd
12
  import pytz
@@ -15,24 +17,32 @@ import re
15
  import requests
16
  import shutil
17
  import streamlit as st
 
18
  import sys
 
19
  import time
 
20
  import torch
21
  import zipfile
22
 
23
  from audio_recorder_streamlit import audio_recorder
 
 
24
  from contextlib import redirect_stdout
25
  from dataclasses import dataclass
26
  from datetime import datetime
27
  from diffusers import StableDiffusionPipeline
 
 
28
  from io import BytesIO
29
- from moviepy import VideoFileClip # Updated import
30
  from openai import OpenAI
31
  from PIL import Image
32
  from PyPDF2 import PdfReader
33
  from transformers import AutoModelForCausalLM, AutoTokenizer, AutoModel
34
  from typing import Optional
35
-
 
36
 
37
  # Initialize OpenAI client
38
  client = OpenAI(api_key=os.getenv('OPENAI_API_KEY'), organization=os.getenv('OPENAI_ORG_ID'))
@@ -60,13 +70,18 @@ st.set_page_config(
60
  )
61
 
62
  # Session state initialization
63
- for key in ['history', 'builder', 'model_loaded', 'processing', 'asset_checkboxes', 'downloaded_pdfs', 'unique_counter', 'messages']:
64
- st.session_state.setdefault(key, [] if key in ['history', 'messages'] else {} if key in ['asset_checkboxes', 'downloaded_pdfs', 'processing'] else None if key == 'builder' else 0 if key == 'unique_counter' else False)
 
 
65
  st.session_state.setdefault('selected_model_type', "Causal LM")
66
  st.session_state.setdefault('selected_model', "None")
67
  st.session_state.setdefault('gallery_size', 2)
68
  st.session_state.setdefault('asset_gallery_container', st.sidebar.empty())
 
 
69
 
 
70
  @dataclass
71
  class ModelConfig:
72
  name: str
@@ -93,6 +108,11 @@ class ModelBuilder:
93
  self.config = None
94
  self.model = None
95
  self.tokenizer = None
 
 
 
 
 
96
  def load_model(self, model_path: str, config: Optional[ModelConfig] = None):
97
  with st.spinner(f"Loading {model_path}... ⏳"):
98
  self.model = AutoModelForCausalLM.from_pretrained(model_path)
@@ -102,7 +122,7 @@ class ModelBuilder:
102
  if config:
103
  self.config = config
104
  self.model.to("cuda" if torch.cuda.is_available() else "cpu")
105
- st.success(f"Model loaded! 🎉")
106
  return self
107
  def save_model(self, path: str):
108
  with st.spinner("Saving model... 💾"):
@@ -130,10 +150,11 @@ class DiffusionBuilder:
130
  def generate(self, prompt: str):
131
  return self.pipeline(prompt, num_inference_steps=20).images[0]
132
 
 
133
  def generate_filename(prompt, ext="png"):
134
  central = pytz.timezone('US/Central')
135
  safe_date_time = datetime.now(central).strftime("%m%d_%H%M")
136
- safe_prompt = re.sub(r'[<>:"/\\|?*]', '_', prompt)[:240]
137
  return f"{safe_date_time}_{safe_prompt}.{ext}"
138
 
139
  def get_download_link(file_path, mime_type="application/pdf", label="Download"):
@@ -162,6 +183,7 @@ def download_pdf(url, output_path):
162
  logger.error(f"Failed to download {url}: {e}")
163
  return False
164
 
 
165
  async def process_pdf_snapshot(pdf_path, mode="single"):
166
  start_time = time.time()
167
  status = st.empty()
@@ -248,18 +270,24 @@ def process_text_with_prompt(text, prompt, model="gpt-4o-mini"):
248
  except Exception as e:
249
  return f"Error processing text with GPT: {str(e)}"
250
 
251
- def process_audio(audio_input, prompt):
252
  with open(audio_input, "rb") as file:
253
  transcription = client.audio.transcriptions.create(model="whisper-1", file=file)
254
- response = client.chat.completions.create(model="gpt-4o-mini", messages=[{"role": "user", "content": f"{prompt}\n\n{transcription.text}"}])
255
- return transcription.text, response.choices[0].message.content
 
 
 
 
 
 
256
 
257
  def process_video(video_path, prompt):
258
  base64Frames, audio_path = process_video_frames(video_path)
259
  with open(video_path, "rb") as file:
260
  transcription = client.audio.transcriptions.create(model="whisper-1", file=file)
261
  messages = [{"role": "user", "content": ["These are the frames from the video.", *map(lambda x: {"type": "image_url", "image_url": {"url": f'data:image/jpg;base64,{x}', "detail": "low"}}, base64Frames), {"type": "text", "text": f"The audio transcription is: {transcription.text}\n\n{prompt}"}]}]
262
- response = client.chat.completions.create(model="gpt-4o-mini", messages=messages)
263
  return response.choices[0].message.content
264
 
265
  def process_video_frames(video_path, seconds_per_frame=2):
@@ -300,13 +328,147 @@ def execute_code(code):
300
  finally:
301
  buffer.close()
302
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
303
  # Sidebar
304
  st.sidebar.subheader("Gallery Settings")
305
  st.session_state['gallery_size'] = st.sidebar.slider("Gallery Size", 1, 10, st.session_state['gallery_size'], key="gallery_size_slider")
306
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
307
  # Tabs
308
- tabs = st.tabs(["Camera 📷", "Download 📥", "OCR 🔍", "Build 🌱", "Image Gen 🎨", "PDF 📄", "Image 🖼️", "Audio 🎵", "Video 🎥", "Code 🧑‍💻", "Gallery 📚"])
309
- (tab_camera, tab_download, tab_ocr, tab_build, tab_imggen, tab_pdf, tab_image, tab_audio, tab_video, tab_code, tab_gallery) = tabs
310
 
311
  with tab_camera:
312
  st.header("Camera Snap 📷")
@@ -324,8 +486,11 @@ with tab_camera:
324
 
325
  with tab_download:
326
  st.header("Download PDFs 📥")
327
- url_input = st.text_area("Enter PDF URLs (one per line)", height=200)
328
- if st.button("Download 🤖"):
 
 
 
329
  urls = url_input.strip().split("\n")
330
  progress_bar = st.progress(0)
331
  for idx, url in enumerate(urls):
@@ -464,6 +629,17 @@ with tab_gallery:
464
  elif file.endswith('.mp4'):
465
  st.video(file)
466
 
 
 
 
 
 
 
 
 
 
 
 
467
  # Update gallery in sidebar
468
  def update_gallery():
469
  container = st.session_state['asset_gallery_container']
@@ -497,4 +673,18 @@ for record in log_records:
497
  st.sidebar.subheader("History 📜")
498
  for entry in st.session_state.get("history", []):
499
  if entry:
500
- st.sidebar.write(entry)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
7
  import io
8
  import json
9
  import logging
10
+ import math
11
+ import mistune
12
  import os
13
  import pandas as pd
14
  import pytz
 
17
  import requests
18
  import shutil
19
  import streamlit as st
20
+ import streamlit.components.v1 as components
21
  import sys
22
+ import textract
23
  import time
24
+ import tiktoken
25
  import torch
26
  import zipfile
27
 
28
  from audio_recorder_streamlit import audio_recorder
29
+ from bs4 import BeautifulSoup
30
+ from collections import deque
31
  from contextlib import redirect_stdout
32
  from dataclasses import dataclass
33
  from datetime import datetime
34
  from diffusers import StableDiffusionPipeline
35
+ from gradio_client import Client, handle_file
36
+ from huggingface_hub import InferenceClient
37
  from io import BytesIO
38
+ from moviepy import VideoFileClip
39
  from openai import OpenAI
40
  from PIL import Image
41
  from PyPDF2 import PdfReader
42
  from transformers import AutoModelForCausalLM, AutoTokenizer, AutoModel
43
  from typing import Optional
44
+ from urllib.parse import quote
45
+ from xml.etree import ElementTree as ET
46
 
47
  # Initialize OpenAI client
48
  client = OpenAI(api_key=os.getenv('OPENAI_API_KEY'), organization=os.getenv('OPENAI_ORG_ID'))
 
70
  )
71
 
72
  # Session state initialization
73
+ for key in ['history', 'messages', 'processing', 'asset_checkboxes', 'downloaded_pdfs', 'unique_counter', 'search_queries']:
74
+ st.session_state.setdefault(key, [] if key in ['history', 'messages', 'search_queries'] else {} if key in ['asset_checkboxes', 'downloaded_pdfs', 'processing'] else 0 if key == 'unique_counter' else None)
75
+ st.session_state.setdefault('builder', None)
76
+ st.session_state.setdefault('model_loaded', False)
77
  st.session_state.setdefault('selected_model_type', "Causal LM")
78
  st.session_state.setdefault('selected_model', "None")
79
  st.session_state.setdefault('gallery_size', 2)
80
  st.session_state.setdefault('asset_gallery_container', st.sidebar.empty())
81
+ st.session_state.setdefault('cam0_file', None)
82
+ st.session_state.setdefault('cam1_file', None)
83
 
84
+ # Model configurations
85
  @dataclass
86
  class ModelConfig:
87
  name: str
 
108
  self.config = None
109
  self.model = None
110
  self.tokenizer = None
111
+ self.jokes = [
112
+ "Why did the AI go to therapy? Too many layers to unpack! 😂",
113
+ "Training complete! Time for a binary coffee break. ☕",
114
+ "I told my neural network a joke; it couldn't stop dropping bits! 🤖"
115
+ ]
116
  def load_model(self, model_path: str, config: Optional[ModelConfig] = None):
117
  with st.spinner(f"Loading {model_path}... ⏳"):
118
  self.model = AutoModelForCausalLM.from_pretrained(model_path)
 
122
  if config:
123
  self.config = config
124
  self.model.to("cuda" if torch.cuda.is_available() else "cpu")
125
+ st.success(f"Model loaded! 🎉 {random.choice(self.jokes)}")
126
  return self
127
  def save_model(self, path: str):
128
  with st.spinner("Saving model... 💾"):
 
150
  def generate(self, prompt: str):
151
  return self.pipeline(prompt, num_inference_steps=20).images[0]
152
 
153
+ # Utility functions
154
  def generate_filename(prompt, ext="png"):
155
  central = pytz.timezone('US/Central')
156
  safe_date_time = datetime.now(central).strftime("%m%d_%H%M")
157
+ safe_prompt = re.sub(r'[<>:"/\\|?*\n]', '_', prompt)[:240]
158
  return f"{safe_date_time}_{safe_prompt}.{ext}"
159
 
160
  def get_download_link(file_path, mime_type="application/pdf", label="Download"):
 
183
  logger.error(f"Failed to download {url}: {e}")
184
  return False
185
 
186
+ # Processing functions
187
  async def process_pdf_snapshot(pdf_path, mode="single"):
188
  start_time = time.time()
189
  status = st.empty()
 
270
  except Exception as e:
271
  return f"Error processing text with GPT: {str(e)}"
272
 
273
+ def process_audio(audio_input, text_input=''):
274
  with open(audio_input, "rb") as file:
275
  transcription = client.audio.transcriptions.create(model="whisper-1", file=file)
276
+ st.session_state.messages.append({"role": "user", "content": transcription.text})
277
+ completion = client.chat.completions.create(model="gpt-4o-2024-05-13", messages=[{"role": "user", "content": f"{text_input}\n\n{transcription.text}"}])
278
+ return_text = completion.choices[0].message.content
279
+ filename = generate_filename(transcription.text, "md")
280
+ with open(filename, "w", encoding="utf-8") as f:
281
+ f.write(text_input + "\n\n" + return_text)
282
+ st.session_state.messages.append({"role": "assistant", "content": return_text})
283
+ return transcription.text, return_text
284
 
285
  def process_video(video_path, prompt):
286
  base64Frames, audio_path = process_video_frames(video_path)
287
  with open(video_path, "rb") as file:
288
  transcription = client.audio.transcriptions.create(model="whisper-1", file=file)
289
  messages = [{"role": "user", "content": ["These are the frames from the video.", *map(lambda x: {"type": "image_url", "image_url": {"url": f'data:image/jpg;base64,{x}', "detail": "low"}}, base64Frames), {"type": "text", "text": f"The audio transcription is: {transcription.text}\n\n{prompt}"}]}]
290
+ response = client.chat.completions.create(model="gpt-4o-2024-05-13", messages=messages)
291
  return response.choices[0].message.content
292
 
293
  def process_video_frames(video_path, seconds_per_frame=2):
 
328
  finally:
329
  buffer.close()
330
 
331
+ def extract_python_code(markdown_text):
332
+ pattern = r"```python\s*(.*?)\s*```"
333
+ matches = re.findall(pattern, markdown_text, re.DOTALL)
334
+ return matches
335
+
336
+ # Speech synthesis
337
+ def SpeechSynthesis(result):
338
+ documentHTML5 = f'''
339
+ <!DOCTYPE html>
340
+ <html>
341
+ <head>
342
+ <title>Read It Aloud</title>
343
+ <script type="text/javascript">
344
+ function readAloud() {{
345
+ const text = document.getElementById("textArea").value;
346
+ const speech = new SpeechSynthesisUtterance(text);
347
+ window.speechSynthesis.speak(speech);
348
+ }}
349
+ </script>
350
+ </head>
351
+ <body>
352
+ <h1>🔊 Read It Aloud</h1>
353
+ <textarea id="textArea" rows="10" cols="80">{result}</textarea>
354
+ <br>
355
+ <button onclick="readAloud()">🔊 Read Aloud</button>
356
+ </body>
357
+ </html>
358
+ '''
359
+ components.html(documentHTML5, width=1280, height=300)
360
+
361
+ # ArXiv search
362
+ def search_arxiv(query):
363
+ start_time = time.strftime("%Y-%m-%d %H:%M:%S")
364
+ client = Client("awacke1/Arxiv-Paper-Search-And-QA-RAG-Pattern")
365
+ response1 = client.predict(message="Hello!!", llm_results_use=5, database_choice="Semantic Search", llm_model_picked="mistralai/Mistral-7B-Instruct-v0.2", api_name="/update_with_rag_md")
366
+ Question = f'### 🔎 {query}\r\n'
367
+ References = response1[0]
368
+ References2 = response1[1]
369
+ filename = generate_filename(query, "md")
370
+ with open(filename, "w", encoding="utf-8") as f:
371
+ f.write(Question + References + References2)
372
+ st.session_state.messages.append({"role": "assistant", "content": References + References2})
373
+ response2 = client.predict(query, "mistralai/Mixtral-8x7B-Instruct-v0.1", True, api_name="/ask_llm")
374
+ if len(response2) > 10:
375
+ Answer = response2
376
+ SpeechSynthesis(Answer)
377
+ results = Question + '\r\n' + Answer + '\r\n' + References + '\r\n' + References2
378
+ return results
379
+ return References + References2
380
+
381
+ # Glossary data
382
+ roleplaying_glossary = {
383
+ "🤖 AI Concepts": {
384
+ "MoE (Mixture of Experts) 🧠": [
385
+ "As a leading AI health researcher, provide an overview of MoE, MAS, memory, and mirroring in healthcare applications.",
386
+ "Explain how MoE and MAS can be leveraged to create AGI and AMI systems for healthcare, as an AI architect."
387
+ ],
388
+ "Multi Agent Systems (MAS) 🤝": [
389
+ "As a renowned MAS researcher, describe the key characteristics of distributed, autonomous, and cooperative MAS.",
390
+ "Discuss how MAS is applied in robotics, simulations, and decentralized problem-solving, as an AI engineer."
391
+ ]
392
+ },
393
+ "🛠️ AI Tools & Platforms": {
394
+ "ChatDev 💬": [
395
+ "As a chatbot developer, ask about the features and capabilities ChatDev offers for building conversational AI.",
396
+ "Inquire about the pre-built assets, integrations, and multi-platform support in ChatDev, as a product manager."
397
+ ]
398
+ }
399
+ }
400
+
401
+ def display_glossary_grid(roleplaying_glossary):
402
+ search_urls = {
403
+ "🚀🌌ArXiv": lambda k: f"/?q={quote(k)}",
404
+ "📖": lambda k: f"https://en.wikipedia.org/wiki/{quote(k)}",
405
+ "🔍": lambda k: f"https://www.google.com/search?q={quote(k)}"
406
+ }
407
+ for category, details in roleplaying_glossary.items():
408
+ st.write(f"### {category}")
409
+ cols = st.columns(len(details))
410
+ for idx, (game, terms) in enumerate(details.items()):
411
+ with cols[idx]:
412
+ st.markdown(f"#### {game}")
413
+ for term in terms:
414
+ links_md = ' '.join([f"[{emoji}]({url(term)})" for emoji, url in search_urls.items()])
415
+ st.markdown(f"**{term}** <small>{links_md}</small>", unsafe_allow_html=True)
416
+
417
+ # File operations
418
+ def create_zip_of_files(files):
419
+ zip_name = "assets.zip"
420
+ with zipfile.ZipFile(zip_name, 'w') as zipf:
421
+ for file in files:
422
+ zipf.write(file)
423
+ return zip_name
424
+
425
+ def get_zip_download_link(zip_file):
426
+ with open(zip_file, 'rb') as f:
427
+ data = f.read()
428
+ b64 = base64.b64encode(data).decode()
429
+ return f'<a href="data:application/zip;base64,{b64}" download="{zip_file}">Download All</a>'
430
+
431
  # Sidebar
432
  st.sidebar.subheader("Gallery Settings")
433
  st.session_state['gallery_size'] = st.sidebar.slider("Gallery Size", 1, 10, st.session_state['gallery_size'], key="gallery_size_slider")
434
 
435
+ # File sidebar
436
+ def FileSidebar():
437
+ all_files = glob.glob("*.md")
438
+ all_files = [file for file in all_files if len(os.path.splitext(file)[0]) >= 10]
439
+ all_files.sort(key=lambda x: (os.path.splitext(x)[1], x), reverse=True)
440
+ Files1, Files2 = st.sidebar.columns(2)
441
+ with Files1:
442
+ if st.button("🗑 Delete All"):
443
+ for file in all_files:
444
+ os.remove(file)
445
+ st.rerun()
446
+ with Files2:
447
+ if st.button("⬇️ Download"):
448
+ zip_file = create_zip_of_files(all_files)
449
+ st.sidebar.markdown(get_zip_download_link(zip_file), unsafe_allow_html=True)
450
+ for file in all_files:
451
+ col1, col2, col3, col4 = st.sidebar.columns([1, 6, 1, 1])
452
+ with col1:
453
+ if st.button("🌐", key=f"md_{file}"):
454
+ with open(file, "r", encoding='utf-8') as f:
455
+ st.markdown(f.read())
456
+ with col2:
457
+ st.markdown(get_download_link(file, "text/markdown", file))
458
+ with col3:
459
+ if st.button("📂", key=f"open_{file}"):
460
+ with open(file, "r", encoding='utf-8') as f:
461
+ st.text_area("File Contents", f.read(), height=300)
462
+ with col4:
463
+ if st.button("🗑", key=f"delete_{file}"):
464
+ os.remove(file)
465
+ st.rerun()
466
+
467
+ FileSidebar()
468
+
469
  # Tabs
470
+ tabs = st.tabs(["Camera 📷", "Download 📥", "OCR 🔍", "Build 🌱", "Image Gen 🎨", "PDF 📄", "Image 🖼️", "Audio 🎵", "Video 🎥", "Code 🧑‍💻", "Gallery 📚", "Search 🔎", "Glossary 📖"])
471
+ (tab_camera, tab_download, tab_ocr, tab_build, tab_imggen, tab_pdf, tab_image, tab_audio, tab_video, tab_code, tab_gallery, tab_search, tab_glossary) = tabs
472
 
473
  with tab_camera:
474
  st.header("Camera Snap 📷")
 
486
 
487
  with tab_download:
488
  st.header("Download PDFs 📥")
489
+ if st.button("Examples 📚"):
490
+ example_urls = ["https://arxiv.org/pdf/2308.03892", "https://arxiv.org/pdf/1912.01703"]
491
+ st.session_state['pdf_urls'] = "\n".join(example_urls)
492
+ url_input = st.text_area("Enter PDF URLs (one per line)", value=st.session_state.get('pdf_urls', ""), height=200)
493
+ if st.button("Robo-Download 🤖"):
494
  urls = url_input.strip().split("\n")
495
  progress_bar = st.progress(0)
496
  for idx, url in enumerate(urls):
 
629
  elif file.endswith('.mp4'):
630
  st.video(file)
631
 
632
+ with tab_search:
633
+ st.header("ArXiv Search 🔎")
634
+ query = st.text_input("Search ArXiv", "")
635
+ if query:
636
+ result = search_arxiv(query)
637
+ st.markdown(result)
638
+
639
+ with tab_glossary:
640
+ st.header("Glossary 📖")
641
+ display_glossary_grid(roleplaying_glossary)
642
+
643
  # Update gallery in sidebar
644
  def update_gallery():
645
  container = st.session_state['asset_gallery_container']
 
673
  st.sidebar.subheader("History 📜")
674
  for entry in st.session_state.get("history", []):
675
  if entry:
676
+ st.sidebar.write(entry)
677
+
678
+ # Chatbot
679
+ if prompt := st.chat_input("GPT-4o Multimodal ChatBot - What can I help you with?"):
680
+ st.session_state.messages.append({"role": "user", "content": prompt})
681
+ with st.chat_message("user"):
682
+ st.markdown(prompt)
683
+ with st.chat_message("assistant"):
684
+ completion = client.chat.completions.create(model="gpt-4o-2024-05-13", messages=st.session_state.messages, stream=True)
685
+ response = ""
686
+ for chunk in completion:
687
+ if chunk.choices[0].delta.content:
688
+ response += chunk.choices[0].delta.content
689
+ st.write(response)
690
+ st.session_state.messages.append({"role": "assistant", "content": response})