DanyaalMajid commited on
Commit
0ff7c7e
1 Parent(s): f21cd9a
Files changed (2) hide show
  1. app.py +105 -0
  2. requirements.txt +5 -0
app.py CHANGED
@@ -0,0 +1,105 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import time
2
+ import streamlit as st
3
+ from llama_index import ServiceContext, StorageContext, set_global_service_context, VectorStoreIndex
4
+ from llama_index.embeddings import LangchainEmbedding
5
+ from langchain.embeddings.huggingface import HuggingFaceEmbeddings
6
+ from llama_index.llms import LlamaCPP
7
+ from llama_index.llms.llama_utils import messages_to_prompt, completion_to_prompt
8
+ from PyPDF2 import PdfReader
9
+
10
+ # LLM Intialization
11
+ llm = LlamaCPP(
12
+ model_url=None, # We'll load locally.
13
+ # Trying small version of an already small model
14
+ model_path='./Models/phi-2.Q4_K_M.gguf',
15
+ temperature=0.1,
16
+ max_new_tokens=512,
17
+ context_window=2048, # Phi-2 2K context window - this could be a limitation for RAG as it has to put the content into this context window
18
+ generate_kwargs={},
19
+ # set to at least 1 to use GPU
20
+ # This is small model and there's no indication of layers offloaded to the GPU
21
+ model_kwargs={"n_gpu_layers": 0},
22
+ messages_to_prompt=messages_to_prompt,
23
+ completion_to_prompt=completion_to_prompt,
24
+ verbose=True
25
+ )
26
+
27
+ # Embedding Initialization
28
+ embed_model = LangchainEmbedding(
29
+ HuggingFaceEmbeddings(model_name="BAAI/bge-small-en-v1.5")
30
+ )
31
+
32
+ # Service Context
33
+ service_context = ServiceContext.from_defaults(
34
+ chunk_size=128, # Number of tokens in each chunk
35
+ chunk_overlap=20,
36
+ # This should be automatically set with the model metadata but we'll force it to ensure wit is
37
+ context_window=2048,
38
+ num_output=768, # Maximum output from the LLM, let's put this at 512 to ensure LlamaIndex saves that "space" for the output
39
+ llm=llm,
40
+ embed_model=embed_model
41
+ )
42
+ set_global_service_context(service_context)
43
+
44
+ # Storage Context
45
+ storage_context = StorageContext.from_defaults()
46
+
47
+
48
+ # Model Specific Prompt
49
+ def modelspecific_prompt(promptmessage):
50
+ # Model Specific Prompt
51
+ # As per https://huggingface.co/TheBloke/phi-2-GGUF
52
+ return f"Instruct: {promptmessage}\nOutput:"
53
+
54
+
55
+ # PDF to Text
56
+ def extract_text_from_pdf(pdf):
57
+ pdf_reader = PdfReader(pdf)
58
+ return ''.join(page.extract_text() for page in pdf_reader.pages)
59
+
60
+
61
+ st.title("Llama-CPP Local LLM with RAG (Phi-2 + TinyLlama)")
62
+
63
+
64
+ pdf = st.file_uploader("Upload a PDF file", type=["pdf"])
65
+
66
+ if pdf is not None:
67
+ documents = extract_text_from_pdf(pdf)
68
+ nodes = (service_context.node_parser.get_nodes_from_documents(documents))
69
+ storage_context.docstore.add_documents(nodes)
70
+ index = (VectorStoreIndex.from_documents(
71
+ documents, service_context=service_context, storage_context=storage_context, llm=llm))
72
+ chat_engine = index.as_chat_engine(chat_mode="simple", verbose=True)
73
+
74
+ # Initialize chat history
75
+ if "messages" not in st.session_state:
76
+ st.session_state.messages = []
77
+
78
+ # Display chat messages from history on app rerun
79
+ for message in st.session_state.messages:
80
+ with st.chat_message(message["role"]):
81
+ st.markdown(message["content"])
82
+
83
+ # Accept user input
84
+ if prompt := st.chat_input("What is up?"):
85
+ # Add user message to chat history
86
+ st.session_state.messages.append({"role": "user", "content": prompt})
87
+ # Display user message in chat message container
88
+ with st.chat_message("user"):
89
+ st.markdown(prompt)
90
+
91
+ # Display assistant response in chat message container
92
+ with st.chat_message("assistant"):
93
+ message_placeholder = st.empty()
94
+ full_response = ""
95
+ assistant_response = chat_engine.chat(modelspecific_prompt(prompt))
96
+ # Simulate stream of response with milliseconds delay
97
+ for chunk in assistant_response.split():
98
+ full_response += chunk + " "
99
+ time.sleep(0.05)
100
+ # Add a blinking cursor to simulate typing
101
+ message_placeholder.markdown(full_response + "▌")
102
+ message_placeholder.markdown(full_response)
103
+ # Add assistant response to chat history
104
+ st.session_state.messages.append(
105
+ {"role": "assistant", "content": full_response})
requirements.txt CHANGED
@@ -0,0 +1,5 @@
 
 
 
 
 
 
1
+ streamlit
2
+ llama-index
3
+ langchain
4
+ PyPDF2
5
+ sentence_transformers