pradeepsengarr commited on
Commit
ea914de
Β·
verified Β·
1 Parent(s): dab1894

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +55 -109
app.py CHANGED
@@ -1,125 +1,71 @@
1
  import os
 
2
  import gradio as gr
3
- import fitz # PyMuPDF
4
  import faiss
5
- import numpy as np
6
- from sentence_transformers import SentenceTransformer
7
- from transformers import AutoTokenizer
8
- from auto_gptq import AutoGPTQForCausalLM
9
  from langchain.text_splitter import RecursiveCharacterTextSplitter
10
  from huggingface_hub import login
11
 
12
- # Authenticate
13
- hf_token = os.environ.get("HUGGINGFACE_TOKEN")
14
  if not hf_token:
15
- raise ValueError("Hugging Face token not found.")
16
  login(token=hf_token)
17
 
18
- # Load embedding model
19
- embed_model = SentenceTransformer("BAAI/bge-base-en-v1.5")
20
-
21
- # Load 4-bit quantized Mistral model
22
  model_id = "TheBloke/Mistral-7B-Instruct-v0.1-GPTQ"
23
- tokenizer = AutoTokenizer.from_pretrained(model_id, use_fast=True)
24
- model = AutoGPTQForCausalLM.from_quantized(
25
- model_id,
26
- use_safetensors=True,
27
- trust_remote_code=True,
28
- device_map="auto"
29
- )
30
-
31
- # Internal state
32
- index = None
33
- doc_texts = []
34
-
35
- # PDF/TXT text extraction
36
- def extract_text(file):
37
- try:
38
- text = ""
39
- file_path = file.name if hasattr(file, 'name') else file
40
- if file_path.endswith(".pdf"):
41
- with fitz.open(file_path) as doc:
42
- for page in doc:
43
- text += page.get_text()
44
- elif file_path.endswith(".txt"):
45
- with open(file_path, "r", encoding="utf-8") as f:
46
- text = f.read()
47
- else:
48
- return "❌ Unsupported file type."
49
- return text
50
- except Exception as e:
51
- return f"❌ Error extracting text: {e}"
52
-
53
- # Preprocess and embed
54
- def process_file(file):
55
- global index, doc_texts
56
- try:
57
- text = extract_text(file)
58
- if text.startswith("❌"):
59
- return text
60
-
61
- text = text[:15000] # Limit size
62
- splitter = RecursiveCharacterTextSplitter(chunk_size=300, chunk_overlap=50)
63
- doc_texts = splitter.split_text(text)
64
-
65
- if not doc_texts:
66
- return "❌ Document could not be split."
67
-
68
- embeddings = embed_model.encode(doc_texts, convert_to_numpy=True)
69
- dim = embeddings.shape[1]
70
- index = faiss.IndexFlatL2(dim)
71
- index.add(embeddings)
72
-
73
- return "βœ… Document processed. Ask your question below."
74
- except Exception as e:
75
- return f"❌ Error processing file: {e}"
76
-
77
- # Generate answer using context
78
- def generate_answer(question):
79
- global index, doc_texts
80
- try:
81
- if index is None or not doc_texts:
82
- return "⚠️ Please upload and process a document first."
83
-
84
- question_emb = embed_model.encode([question], convert_to_numpy=True)
85
- _, I = index.search(question_emb, k=3)
86
- context = "\n".join([doc_texts[i] for i in I[0]])
87
-
88
- prompt = (
89
- f"You are a helpful assistant. Use the context below to answer clearly.\n\n"
90
- f"Context:\n{context}\n\n"
91
- f"Question: {question}\n\n"
92
- f"Answer:"
93
- )
94
-
95
- inputs = tokenizer(prompt, return_tensors="pt").to(model.device)
96
- output = model.generate(
97
- **inputs,
98
- max_new_tokens=150,
99
- do_sample=True,
100
- temperature=0.7,
101
- top_k=50,
102
- top_p=0.95
103
- )
104
- answer = tokenizer.decode(output[0], skip_special_tokens=True)
105
- return answer.split("Answer:")[-1].strip()
106
- except Exception as e:
107
- return f"❌ Error generating answer: {e}"
108
-
109
- # Gradio UI
110
- with gr.Blocks(title="πŸ“„ Document Q&A (Mistral 4-bit)") as demo:
111
- gr.Markdown("<h1 style='text-align: center;'>πŸ“„ Document Q&A with Mistral 4-bit</h1>")
112
- gr.Markdown("Upload a PDF or TXT and ask questions. Powered by Mistral-7B GPTQ.")
113
 
114
  with gr.Row():
115
- file_input = gr.File(label="Upload Document", file_types=[".pdf", ".txt"])
116
- upload_output = gr.Textbox(label="Upload Status")
 
 
117
 
118
  with gr.Row():
119
- question_input = gr.Textbox(label="Ask a Question", placeholder="e.g. What is this document about?")
120
- answer_output = gr.Textbox(label="Answer")
 
 
121
 
122
- file_input.change(fn=process_file, inputs=file_input, outputs=upload_output)
123
- question_input.submit(fn=generate_answer, inputs=question_input, outputs=answer_output)
124
 
125
- demo.launch(show_error=True)
 
1
  import os
2
+ import torch
3
  import gradio as gr
 
4
  import faiss
5
+ from transformers import AutoTokenizer, pipeline
6
+ from langchain_community.vectorstores import FAISS
7
+ from langchain_community.document_loaders import PyPDFLoader
8
+ from langchain_community.embeddings import HuggingFaceEmbeddings
9
  from langchain.text_splitter import RecursiveCharacterTextSplitter
10
  from huggingface_hub import login
11
 
12
+ # πŸ” Authenticate with Hugging Face using token stored in Secrets
13
+ hf_token = os.getenv("HUGGINGFACE_TOKEN")
14
  if not hf_token:
15
+ raise ValueError("❌ HUGGINGFACE_TOKEN not set in environment variables.")
16
  login(token=hf_token)
17
 
18
+ # πŸ” Load model and tokenizer
 
 
 
19
  model_id = "TheBloke/Mistral-7B-Instruct-v0.1-GPTQ"
20
+ tokenizer = AutoTokenizer.from_pretrained(model_id, use_auth_token=True)
21
+ pipe = pipeline("text-generation", model=model_id, tokenizer=tokenizer,
22
+ torch_dtype=torch.float16, device_map="auto", use_auth_token=True)
23
+
24
+ # πŸ”Ž Sentence transformer for embeddings
25
+ embed_model = HuggingFaceEmbeddings(model_name="sentence-transformers/all-MiniLM-L6-v2")
26
+
27
+ # Global store for vector DB
28
+ db = None
29
+
30
+ def process_pdf(pdf_path):
31
+ """Load, chunk, embed and index PDF into FAISS."""
32
+ loader = PyPDFLoader(pdf_path)
33
+ pages = loader.load()
34
+ text_splitter = RecursiveCharacterTextSplitter(chunk_size=500, chunk_overlap=50)
35
+ docs = text_splitter.split_documents(pages)
36
+
37
+ global db
38
+ db = FAISS.from_documents(docs, embed_model)
39
+ return "βœ… PDF processed successfully. Ask your questions now."
40
+
41
+ def query_answer(question):
42
+ if not db:
43
+ return "⚠️ Please upload and process a PDF first."
44
+
45
+ docs = db.similarity_search(question, k=3)
46
+ context = "\n".join([doc.page_content for doc in docs])
47
+ prompt = f"[INST] You are a helpful assistant. Use the context below to answer the question:\n\nContext:\n{context}\n\nQuestion: {question}\n\nAnswer: [/INST]"
48
+
49
+ result = pipe(prompt, max_new_tokens=256, do_sample=True, top_k=5)[0]["generated_text"]
50
+ return result.replace(prompt, "").strip()
51
+
52
+ # πŸ”§ Gradio UI
53
+ with gr.Blocks() as demo:
54
+ gr.Markdown("# πŸ“„ Document Q&A using Mistral-GPTQ")
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
55
 
56
  with gr.Row():
57
+ pdf_file = gr.File(label="Upload PDF", type="filepath")
58
+ upload_btn = gr.Button("Process PDF")
59
+
60
+ status = gr.Textbox(label="Status", interactive=False)
61
 
62
  with gr.Row():
63
+ user_question = gr.Textbox(label="Ask a Question")
64
+ ask_btn = gr.Button("Get Answer")
65
+
66
+ answer = gr.Textbox(label="Answer", lines=10)
67
 
68
+ upload_btn.click(process_pdf, inputs=pdf_file, outputs=status)
69
+ ask_btn.click(query_answer, inputs=user_question, outputs=answer)
70
 
71
+ demo.launch()