Spaces:
Sleeping
Sleeping
File size: 4,920 Bytes
5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 2987ac4 e4e6dc4 2987ac4 e4e6dc4 2987ac4 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 5ca6388 e4e6dc4 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 |
import os
import gradio as gr
from llama_index.core import SimpleDirectoryReader, VectorStoreIndex
from llama_index.embeddings.mixedbreadai import MixedbreadAIEmbedding
from llama_index.llms.groq import Groq
from llama_parse import LlamaParse
# ββββββββββββββββββββββββββββββββ
# 1. Check environment variables
# ββββββββββββββββββββββββββββββββ
llama_cloud_key = os.getenv("LLAMA_CLOUD_API_KEY")
groq_key = os.getenv("GROQ_API_KEY")
mxbai_key = os.getenv("MXBAI_API_KEY")
if not (llama_cloud_key and groq_key and mxbai_key):
raise EnvironmentError(
"LLAMA_CLOUD_API_KEY, GROQ_API_KEY and MXBAI_API_KEY must be set."
)
# ββββββββββββββββββββββββββββββββ
# 2. Model / parser setup
# ββββββββββββββββββββββββββββββββ
LLM_MODEL = "llama-3.1-70b-versatile"
EMBED_MODEL = "mixedbread-ai/mxbai-embed-large-v1"
parser = LlamaParse(api_key=llama_cloud_key, result_type="markdown")
file_extractor = {ext: parser for ext in (
".pdf", ".docx", ".doc", ".txt", ".csv", ".xlsx",
".pptx", ".html", ".jpg", ".jpeg", ".png", ".webp", ".svg",
)}
embed_model = MixedbreadAIEmbedding(api_key=mxbai_key, model_name=EMBED_MODEL)
llm = Groq(model=LLM_MODEL, api_key=groq_key)
# Global cache for the current document
vector_index = None
# ββββββββββββββββββββββββββββββββ
# 3. Helper functions
# ββββββββββββββββββββββββββββββββ
def load_files(file_path: str) -> str:
"""Parse the uploaded document and build a vector index."""
global vector_index
if not file_path:
return "β οΈ No file selected."
if not any(file_path.endswith(ext) for ext in file_extractor):
return ("β οΈ Unsupported file type. "
f"Allowed: {', '.join(file_extractor.keys())}")
docs = SimpleDirectoryReader(
input_files=[file_path], file_extractor=file_extractor
).load_data()
vector_index = VectorStoreIndex.from_documents(docs, embed_model=embed_model)
return f"β
Parsed **{os.path.basename(file_path)}**. Ask away!"
def respond(message: str, history: list) -> str:
"""Chat handler. Streams partial tokens back to the UI."""
if vector_index is None:
return "β‘οΈ Please upload a document first."
query_engine = vector_index.as_query_engine(streaming=True, llm=llm)
streaming_resp = query_engine.query(message)
partial = ""
for chunk in streaming_resp.response_gen:
partial += chunk
yield partial # <β streaming to the frontend
def clear_state():
"""Reset everything."""
global vector_index
vector_index = None
return [None, ""]
# ββββββββββββββββββββββββββββββββ
# 4. Gradio UI
# ββββββββββββββββββββββββββββββββ
with gr.Blocks(
theme=gr.themes.Default(
primary_hue="green",
secondary_hue="blue",
font=[gr.themes.GoogleFont("Poppins")]
),
css="footer {visibility: hidden}"
) as demo:
gr.Markdown("<h1 style='text-align:center'>DataCamp Doc Q&A π€π</h1>")
with gr.Row():
with gr.Column(scale=1):
file_input = gr.File(file_count="single",
type="filepath",
label="Upload document")
with gr.Row():
submit_btn = gr.Button("Submit", variant="primary")
clear_btn = gr.Button("Clear")
status_box = gr.Markdown()
with gr.Column(scale=3):
chat = gr.ChatInterface(
fn=respond,
chatbot=gr.Chatbot(height=300),
show_progress="full", # keep the nice progress bar
textbox=gr.Textbox(
placeholder="Ask a question about the uploaded documentβ¦",
container=False,
),
)
submit_btn.click(load_files, inputs=file_input, outputs=status_box)
clear_btn.click(clear_state, outputs=[file_input, status_box])
# Disable OpenAPI generation (avoids the bool/βconstβ bug) β¦
demo.queue(api_open=False)
# ββββββββββββββββββββββββββββββββ
# 5. Launch
# ββββββββββββββββββββββββββββββββ
if __name__ == "__main__":
# β¦and make a public share link so the container doesnβt choke on localhost
demo.launch(share=True, server_name="0.0.0.0", server_port=7860)
|