diff --git a/examples/Getting_to_know_Llama.ipynb b/examples/Getting_to_know_Llama.ipynb
index 8944d3d1838483f5457ce1dcbbd840826d8132ab..c751021cb004bcf2ecdb56cc50e938698bf25ec3 100644
--- a/examples/Getting_to_know_Llama.ipynb
+++ b/examples/Getting_to_know_Llama.ipynb
@@ -1 +1 @@
-{"cells":[{"cell_type":"markdown","source":["![Meta---Logo@1x.jpg](data:image/jpeg;base64,/9j/4QAYRXhpZgAASUkqAAgAAAAAAAAAAAAAAP/sABFEdWNreQABAAQAAABkAAD/4QMxaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wLwA8P3hwYWNrZXQgYmVnaW49Iu+7vyIgaWQ9Ilc1TTBNcENlaGlIenJlU3pOVGN6a2M5ZCI/PiA8eDp4bXBtZXRhIHhtbG5zOng9ImFkb2JlOm5zOm1ldGEvIiB4OnhtcHRrPSJBZG9iZSBYTVAgQ29yZSA5LjAtYzAwMCA3OS5kYTRhN2U1ZWYsIDIwMjIvMTEvMjItMTM6NTA6MDcgICAgICAgICI+IDxyZGY6UkRGIHhtbG5zOnJkZj0iaHR0cDovL3d3dy53My5vcmcvMTk5OS8wMi8yMi1yZGYtc3ludGF4LW5zIyI+IDxyZGY6RGVzY3JpcHRpb24gcmRmOmFib3V0PSIiIHhtbG5zOnhtcD0iaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wLyIgeG1sbnM6eG1wTU09Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9tbS8iIHhtbG5zOnN0UmVmPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvc1R5cGUvUmVzb3VyY2VSZWYjIiB4bXA6Q3JlYXRvclRvb2w9IkFkb2JlIFBob3Rvc2hvcCAyNC4xIChNYWNpbnRvc2gpIiB4bXBNTTpJbnN0YW5jZUlEPSJ4bXAuaWlkOjlDN0Y5QzBDNEIxRDExRUU5MjgwQUNGNjU1QzlDQjREIiB4bXBNTTpEb2N1bWVudElEPSJ4bXAuZGlkOjlDN0Y5QzBENEIxRDExRUU5MjgwQUNGNjU1QzlDQjREIj4gPHhtcE1NOkRlcml2ZWRGcm9tIHN0UmVmOmluc3RhbmNlSUQ9InhtcC5paWQ6OUM3RjlDMEE0QjFEMTFFRTkyODBBQ0Y2NTVDOUNCNEQiIHN0UmVmOmRvY3VtZW50SUQ9InhtcC5kaWQ6OUM3RjlDMEI0QjFEMTFFRTkyODBBQ0Y2NTVDOUNCNEQiLz4gPC9yZGY6RGVzY3JpcHRpb24+IDwvcmRmOlJERj4gPC94OnhtcG1ldGE+IDw/eHBhY2tldCBlbmQ9InIiPz7/7gAOQWRvYmUAZMAAAAAB/9sAhAABAQEBAQEBAQEBAQEB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)"],"metadata":{"id":"RJSnI0Xy-kCm"}},{"cell_type":"markdown","metadata":{"id":"LERqQn5v8-ak"},"source":["# **Getting to know Llama 2: Everything you need to start building**\n","Our goal in this session is to provide a guided tour of Llama 2, including understanding different Llama 2 models, how and where to access them, Generative AI and Chatbot architectures, prompt engineering, RAG (Retrieval Augmented Generation), Fine-tuning and more. All this is implemented with a starter code for you to take it and use it in your Llama 2 projects."]},{"cell_type":"markdown","source":["##**0 - Prerequisites**\n","* Basic understanding of Large Language Models\n","\n","* Basic understanding of Python"],"metadata":{"id":"ioVMNcTesSEk"}},{"cell_type":"code","execution_count":null,"metadata":{"id":"ktEA7qXmwdUM"},"outputs":[],"source":["# presentation layer code\n","\n","import base64\n","from IPython.display import Image, display\n","import matplotlib.pyplot as plt\n","\n","def mm(graph):\n","  graphbytes = graph.encode(\"ascii\")\n","  base64_bytes = base64.b64encode(graphbytes)\n","  base64_string = base64_bytes.decode(\"ascii\")\n","  display(Image(url=\"https://mermaid.ink/img/\" + base64_string))\n","\n","def genai_app_arch():\n","  mm(\"\"\"\n","  flowchart TD\n","    A[Users] --> B(Applications e.g. mobile, web)\n","    B --> |Hosted API|C(Platforms e.g. Custom, HuggingFace, Replicate)\n","    B -- optional --> E(Frameworks e.g. LangChain)\n","    C-->|User Input|D[Llama 2]\n","    D-->|Model Output|C\n","    E --> C\n","    classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def rag_arch():\n","  mm(\"\"\"\n","  flowchart TD\n","    A[User Prompts] --> B(Frameworks e.g. LangChain)\n","    B <--> |Database, Docs, XLS|C[fa:fa-database External Data]\n","    B -->|API|D[Llama 2]\n","    classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def llama2_family():\n","  mm(\"\"\"\n","  graph LR;\n","      llama-2 --> llama-2-7b\n","      llama-2 --> llama-2-13b\n","      llama-2 --> llama-2-70b\n","      llama-2-7b --> llama-2-7b-chat\n","      llama-2-13b --> llama-2-13b-chat\n","      llama-2-70b --> llama-2-70b-chat\n","      classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def apps_and_llms():\n","  mm(\"\"\"\n","  graph LR;\n","    users --> apps\n","    apps --> frameworks\n","    frameworks --> platforms\n","    platforms --> Llama 2\n","    classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","import ipywidgets as widgets\n","from IPython.display import display, Markdown\n","\n","# Create a text widget\n","API_KEY = widgets.Password(\n","    value='',\n","    placeholder='',\n","    description='API_KEY:',\n","    disabled=False\n",")\n","\n","def md(t):\n","  display(Markdown(t))\n","\n","def bot_arch():\n","  mm(\"\"\"\n","  graph LR;\n","  user --> prompt\n","  prompt --> i_safety\n","  i_safety --> context\n","  context --> Llama_2\n","  Llama_2 --> output\n","  output --> o_safety\n","  i_safety --> memory\n","  o_safety --> memory\n","  memory --> context\n","  o_safety --> user\n","  classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def fine_tuned_arch():\n","  mm(\"\"\"\n","  graph LR;\n","      Custom_Dataset --> Pre-trained_Llama\n","      Pre-trained_Llama --> Fine-tuned_Llama\n","      Fine-tuned_Llama --> RLHF\n","      RLHF --> |Loss:Cross-Entropy|Fine-tuned_Llama\n","      classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def load_data_faiss_arch():\n","  mm(\"\"\"\n","  graph LR;\n","      documents --> textsplitter\n","      textsplitter --> embeddings\n","      embeddings --> vectorstore\n","      classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def mem_context():\n","  mm(\"\"\"\n","      graph LR\n","      context(text)\n","      user_prompt --> context\n","      instruction --> context\n","      examples --> context\n","      memory --> context\n","      context --> tokenizer\n","      tokenizer --> embeddings\n","      embeddings --> LLM\n","      classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n"]},{"cell_type":"markdown","source":["##**1 - Understanding Llama 2**"],"metadata":{"id":"i4Np_l_KtIno"}},{"cell_type":"markdown","metadata":{"id":"PGPSI3M5PGTi"},"source":["### **1.1 - What is Llama 2?**\n","\n","* State of the art (SOTA), Open Source LLM\n","* 7B, 13B, 70B\n","* Pretrained + Chat\n","* Choosing model: Size, Quality, Cost, Speed\n","* [Research paper](https://ai.meta.com/research/publications/llama-2-open-foundation-and-fine-tuned-chat-models/)\n","\n","* [Responsible use guide](https://ai.meta.com/llama/responsible-use-guide/)"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"OXRCC7wexZXd"},"outputs":[],"source":["llama2_family()"]},{"cell_type":"markdown","metadata":{"id":"aYeHVVh45bdT"},"source":["###**1.2 - Accessing Llama 2**\n","* Download + Self Host (on-premise)\n","* Hosted API Platform (e.g. Replicate)\n","\n","* Hosted Container Platform (e.g. Azure, AWS, GCP)\n","\n"]},{"cell_type":"markdown","source":["### **1.3 - Use Cases of Llama 2**\n","* Content Generation\n","* Chatbots\n","* Summarization\n","* Programming (e.g. Code Llama)\n","\n","* and many more..."],"metadata":{"id":"kBuSay8vtzL4"}},{"cell_type":"markdown","source":["##**2 - Using Llama 2**"],"metadata":{"id":"sd54g0OHuqBY"}},{"cell_type":"markdown","metadata":{"id":"h3YGMDJidHtH"},"source":["### **2.1 - Install dependencies**"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"VhN6hXwx7FCp"},"outputs":[],"source":["# Install dependencies and initialize\n","%pip install -qU \\\n","    replicate \\\n","    langchain \\\n","    sentence_transformers \\\n","    pdf2image \\\n","    pdfminer \\\n","    pdfminer.six \\\n","    unstructured \\\n","    faiss-gpu"]},{"cell_type":"code","source":["# model we will use throughout the notebook\n","llama2_13b = \"meta/llama-2-13b-chat:f4e2de70d66816a838a89eeeb621910adffb0dd0baba3976c96980970978018d\""],"metadata":{"id":"Z8Y8qjEjmg50"},"execution_count":null,"outputs":[]},{"cell_type":"code","execution_count":null,"metadata":{"id":"8hkWpqWD28ho"},"outputs":[],"source":["# We will use Replicate hosted cloud environment\n","# Obtain Replicate API key → https://replicate.com/account/api-tokens)\n","# Find the model to use → we will use [`llama-2-13b-chat`](https://replicate.com/lucataco/llama-2-13b-chat)\n","\n","# enter your replicate api token\n","from getpass import getpass\n","import os\n","\n","REPLICATE_API_TOKEN = getpass()\n","os.environ[\"REPLICATE_API_TOKEN\"] = REPLICATE_API_TOKEN\n","\n","# alternatively, you can also store the tokens in environment variables and load it here"]},{"cell_type":"code","source":["# we will use replicate's hosted api\n","import replicate\n","\n","# text completion with input prompt\n","def Completion(prompt):\n","  output = replicate.run(\n","      llama2_13b,\n","      input={\"prompt\": prompt, \"max_new_tokens\":1000}\n","  )\n","  return \"\".join(output)\n","\n","# chat completion with input prompt and system prompt\n","def ChatCompletion(prompt, system_prompt=None):\n","  output = replicate.run(\n","    llama2_13b,\n","    input={\"system_prompt\": system_prompt,\n","            \"prompt\": prompt,\n","            \"max_new_tokens\":1000}\n","  )\n","  return \"\".join(output)"],"metadata":{"id":"bVCHZmETk36v"},"execution_count":null,"outputs":[]},{"cell_type":"markdown","metadata":{"id":"5Jxq0pmf6L73"},"source":["### **2.2 - Basic completion**"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"H93zZBIk6tNU"},"outputs":[],"source":["output = Completion(prompt=\"The typical color of a llama is: \")\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"StccjUDh6W0Q"},"source":["### **2.3 - System prompts**\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"VRnFogxd6rTc"},"outputs":[],"source":["output = ChatCompletion(\n","    prompt=\"The typical color of a llama is: \",\n","    system_prompt=\"respond with only one word\"\n","  )\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"Hp4GNa066pYy"},"source":["### **2.4 - Response formats**\n","* Can support different formatted outputs e.g. text, JSON, etc."]},{"cell_type":"code","source":["output = ChatCompletion(\n","    prompt=\"The typical color of a llama is: \",\n","    system_prompt=\"response in json format\"\n","  )\n","md(output)"],"metadata":{"id":"HTN79h4RptgQ"},"execution_count":null,"outputs":[]},{"cell_type":"markdown","metadata":{"id":"cWs_s9y-avIT"},"source":["## **3 - Gen AI Application Architecture**\n"]},{"cell_type":"code","source":["genai_app_arch()"],"metadata":{"id":"j9BGuI-9AOL5"},"execution_count":null,"outputs":[]},{"cell_type":"markdown","metadata":{"id":"6UlxBtbgys6j"},"source":["##4 - **Chatbot Architecture**\n","* User Prompts\n","* Input Safety\n","* Llama 2\n","* Output Safety\n","\n","* Memory & Context"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"tO5HnB56ys6t"},"outputs":[],"source":["bot_arch()"]},{"cell_type":"markdown","metadata":{"id":"r4DyTLD5ys6t"},"source":["### **4.1 - Chat conversation**\n","* LLMs are stateless\n","* Single Turn\n","\n","* Multi Turn (Memory)\n","\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"EMM_egWMys6u"},"outputs":[],"source":["# example of single turn chat\n","prompt_chat = \"What is the average lifespan of a Llama?\"\n","output = ChatCompletion(prompt=prompt_chat, system_prompt=\"answer the last question in few words\")\n","md(output)"]},{"cell_type":"code","source":["# example without previous context. LLM's are stateless and cannot understand \"they\" without previous context\n","prompt_chat = \"What animal family are they?\"\n","output = ChatCompletion(prompt=prompt_chat, system_prompt=\"answer the last question in few words\")\n","md(output)"],"metadata":{"id":"sZ7uVKDYucgi"},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":["Chat app requires us to send in previous context to LLM to get in valid responses. Below is an example of Multi-turn chat."],"metadata":{"id":"WQl3wmfbyBQ1"}},{"cell_type":"code","source":["# example of multi-turn chat, with storing previous context\n","prompt_chat = \"\"\"\n","User: What is the average lifespan of a Llama?\n","Assistant: Sure! The average lifespan of a llama is around 20-30 years.\n","User: What animal family are they?\n","\"\"\"\n","output = ChatCompletion(prompt=prompt_chat, system_prompt=\"answer the last question\")\n","md(output)"],"metadata":{"id":"t7SZe5fT3HG3"},"execution_count":null,"outputs":[]},{"cell_type":"markdown","metadata":{"id":"moXnmJ_xyD10"},"source":["### **4.2 - Prompt Engineering**\n","Prompt engineering refers to the science of designing effective prompts to get desired responses.\n"]},{"cell_type":"markdown","metadata":{"id":"t-v-FeZ4ztTB"},"source":["#### **4.2.1 - In-Context Learning (e.g. Zero-shot, Few-shot)**\n"," * In-context learning - specific method of prompt engineering where demonstration of task are provided as part of prompt.\n","  1. Zero-shot learning - model is performing tasks without any\n","input examples.\n","  2. Few or “N-Shot” Learning - model is performing and behaving based on input examples in user's prompt.\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"6W71MFNZyRkQ"},"outputs":[],"source":["# Zero-shot example. To get positive/negative/neutral sentiment, we need to give examples in the prompt\n","prompt = '''\n","Classify: I saw a Gecko.\n","Sentiment: ?\n","'''\n","output = ChatCompletion(prompt, system_prompt=\"one word response\")\n","md(output)"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"MCQRjf1Y1RYJ"},"outputs":[],"source":["# By giving examples to Llama, it understands the expected output format.\n","\n","prompt = '''\n","Classify: I love Llamas!\n","Sentiment: Positive\n","Classify: I dont like Snakes.\n","Sentiment: Negative\n","Classify: I saw a Gecko.\n","Sentiment:'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"One word response\")\n","md(output)"]},{"cell_type":"code","source":["# another zero-shot learning\n","prompt = '''\n","QUESTION: Vicuna?\n","ANSWER:'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"one word response\")\n","md(output)"],"metadata":{"id":"8UmdlTmpDZxA"},"execution_count":null,"outputs":[]},{"cell_type":"code","execution_count":null,"metadata":{"id":"M_EcsUo1zqFD"},"outputs":[],"source":["# Another few-shot learning example with formatted prompt.\n","\n","prompt = '''\n","QUESTION: Llama?\n","ANSWER: Yes\n","QUESTION: Alpaca?\n","ANSWER: Yes\n","QUESTION: Rabbit?\n","ANSWER: No\n","QUESTION: Vicuna?\n","ANSWER:'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"one word response\")\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"mbr124Y197xl"},"source":["#### **4.2.2 - Chain of Thought**\n","* \"chain of thought\" or a coherent sequence of ideas is crucial for generating meaningful and contextually relevant responses\n","\n","* Hallucination on word problems"]},{"cell_type":"code","source":["# Standard prompting\n","prompt = '''\n","Llama started with 5 tennis balls. It buys 2 more cans of tennis balls. Each can has 3 tennis balls. How many tennis balls does Llama have now?\n","'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"provide short answer\")\n","md(output)"],"metadata":{"id":"Xn8zmLBQzpgj"},"execution_count":null,"outputs":[]},{"cell_type":"code","source":["# Chain-Of-Thought prompting\n","prompt = '''\n","Llama started with 5 tennis balls. It buys 2 more cans of tennis balls. Each can has 3 tennis balls. How many tennis balls does Llama have now?\n","Let's think step by step.\n","'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"provide short answer\")\n","md(output)"],"metadata":{"id":"lKNOj79o1Kwu"},"execution_count":null,"outputs":[]},{"cell_type":"markdown","metadata":{"id":"C7tDW-AH770Y"},"source":["### **4.3 - Retrieval Augmented Generation (RAG)**\n","* Prompt Eng Limitations (Knowledge cutoff & lack of specialized data)\n","\n","* Langchain\n","\n","Retrieval Augmented Generation(RAG) allows us to retrieve snippets of information from external data sources and augment it to the user's prompt to get tailored responses from Llama 2.\n","\n","\n"]},{"cell_type":"code","source":["rag_arch()"],"metadata":{"id":"Fl1LPltpRQD9"},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":["#### **4.3.1 - LangChain**\n","LangChain is a framework that helps make it easier to implement RAG.\n"],"metadata":{"id":"JJaGMLl_4vYm"}},{"cell_type":"code","execution_count":null,"metadata":{"id":"aoqU3KTcHTWN"},"outputs":[],"source":["# langchain setup\n","from langchain.llms import Replicate\n","# Use the Llama 2 model hosted on Replicate\n","# Temperature: Adjusts randomness of outputs, greater than 1 is random and 0 is deterministic, 0.75 is a good starting value\n","# top_p: When decoding text, samples from the top p percentage of most likely tokens; lower to ignore less likely tokens\n","# max_new_tokens: Maximum number of tokens to generate. A word is generally 2-3 tokens\n","llama_model = Replicate(\n","    model=llama2_13b,\n","    model_kwargs={\"temperature\": 0.75,\"top_p\": 1, \"max_new_tokens\":1000}\n",")"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"gAV2EkZqcruF"},"outputs":[],"source":["# Step 1: load the external data source. In our case, we will load Meta’s “Responsible Use Guide” pdf document.\n","from langchain.document_loaders import OnlinePDFLoader\n","loader = OnlinePDFLoader(\"https://ai.meta.com/static-resource/responsible-use-guide/\")\n","documents = loader.load()\n","\n","# Step 2: Get text splits from document\n","from langchain.text_splitter import RecursiveCharacterTextSplitter\n","text_splitter = RecursiveCharacterTextSplitter(chunk_size=1000, chunk_overlap=20)\n","all_splits = text_splitter.split_documents(documents)\n","\n","# Step 3: Use the embedding model\n","from langchain.vectorstores import FAISS\n","from langchain.embeddings import HuggingFaceEmbeddings\n","model_name = \"sentence-transformers/all-mpnet-base-v2\" # embedding model\n","model_kwargs = {\"device\": \"cpu\"}\n","embeddings = HuggingFaceEmbeddings(model_name=model_name, model_kwargs=model_kwargs)\n","\n","# Step 4: Use vector store to store embeddings\n","vectorstore = FAISS.from_documents(all_splits, embeddings)"]},{"cell_type":"markdown","metadata":{"id":"K2l8S5tBxlkc"},"source":["#### **4.3.2 - LangChain Q&A Retriever**\n","* ConversationalRetrievalChain\n","\n","* Query the Source documents\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"NmEhBe3Kiyre"},"outputs":[],"source":["# Query against your own data\n","from langchain.chains import ConversationalRetrievalChain\n","chain = ConversationalRetrievalChain.from_llm(llama_model, vectorstore.as_retriever(), return_source_documents=True)\n","\n","chat_history = []\n","query = \"How is Meta approaching open science in two short sentences?\"\n","result = chain({\"question\": query, \"chat_history\": chat_history})\n","md(result['answer'])"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"CelLHIvoy2Ke"},"outputs":[],"source":["# This time your previous question and answer will be included as a chat history which will enable the ability\n","# to ask follow up questions.\n","chat_history = [(query, result[\"answer\"])]\n","query = \"How is it benefiting the world?\"\n","result = chain({\"question\": query, \"chat_history\": chat_history})\n","md(result['answer'])"]},{"cell_type":"markdown","source":["## **5 - Fine-Tuning Models**\n","\n","* Limitatons of Prompt Eng and RAG\n","* Fine-Tuning Arch\n","* Types (PEFT, LoRA, QLoRA)\n","* Using PyTorch for Pre-Training & Fine-Tuning\n","\n","* Evals + Quality\n"],"metadata":{"id":"TEvefAWIJONx"}},{"cell_type":"code","source":["fine_tuned_arch()"],"metadata":{"id":"0a9CvJ8YcTzV"},"execution_count":null,"outputs":[]},{"cell_type":"markdown","metadata":{"id":"_8lcgdZa8onC"},"source":["## **6 - Responsible AI**\n","\n","* Power + Responsibility\n","* Hallucinations\n","* Input & Output Safety\n","* Red-teaming (simulating real-world cyber attackers)\n","* [Responsible Use Guide](https://ai.meta.com/llama/responsible-use-guide/)\n","\n"]},{"cell_type":"markdown","metadata":{"id":"pbqb006R-T_k"},"source":["##**7 - Conclusion**\n","* Active research on LLMs and Llama\n","* Leverage the power of Llama and its open community\n","* Safety and responsible use is paramount!\n","\n","* Call-To-Action\n","  * [Replicate Free Credits](https://replicate.fyi/connect2023) for Connect attendees!\n","  * This notebook is available through Llama Github recipes\n","  * Use Llama in your projects and give us feedback\n"]},{"cell_type":"markdown","source":["#### **Resources**\n","- [GitHub - Llama 2](https://github.com/facebookresearch/llama)\n","- [Github - LLama 2 Recipes](https://github.com/facebookresearch/llama-recipes)\n","- [Llama 2](https://ai.meta.com/llama/)\n","- [Research Paper](https://ai.meta.com/research/publications/llama-2-open-foundation-and-fine-tuned-chat-models/)\n","- [Model Card](https://github.com/facebookresearch/llama/blob/main/MODEL_CARD.md)\n","- [Responsible Use Guide](https://ai.meta.com/llama/responsible-use-guide/)\n","- [Acceptable Use Policy](https://ai.meta.com/llama/use-policy/)\n","- [Replicate](https://replicate.com/meta/)\n","- [LangChain](https://www.langchain.com/)\n","\n"],"metadata":{"id":"gSz5dTMxp7xo"}},{"cell_type":"markdown","source":["#### **Authors & Contact**\n","  * asangani@meta.com, [Amit Sangani | LinkedIn](https://www.linkedin.com/in/amitsangani/)\n","  * mohsena@meta.com, [Mohsen Agsen | LinkedIn](https://www.linkedin.com/in/mohsen-agsen-62a9791/)\n"],"metadata":{"id":"V7aI6fhZp-KC"}}],"metadata":{"colab":{"provenance":[],"machine_shape":"hm","collapsed_sections":["ioVMNcTesSEk"],"toc_visible":true},"kernelspec":{"display_name":"Python 3","name":"python3"},"language_info":{"codemirror_mode":{"name":"ipython","version":3},"file_extension":".py","mimetype":"text/x-python","name":"python","nbconvert_exporter":"python","pygments_lexer":"ipython3","version":"3.9.6"}},"nbformat":4,"nbformat_minor":0}
\ No newline at end of file
+{"cells":[{"cell_type":"markdown","metadata":{"id":"RJSnI0Xy-kCm"},"source":["![Meta---Logo@1x.jpg](data:image/jpeg;base64,/9j/4QAYRXhpZgAASUkqAAgAAAAAAAAAAAAAAP/sABFEdWNreQABAAQAAABkAAD/4QMxaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wLwA8P3hwYWNrZXQgYmVnaW49Iu+7vyIgaWQ9Ilc1TTBNcENlaGlIenJlU3pOVGN6a2M5ZCI/PiA8eDp4bXBtZXRhIHhtbG5zOng9ImFkb2JlOm5zOm1ldGEvIiB4OnhtcHRrPSJBZG9iZSBYTVAgQ29yZSA5LjAtYzAwMCA3OS5kYTRhN2U1ZWYsIDIwMjIvMTEvMjItMTM6NTA6MDcgICAgICAgICI+IDxyZGY6UkRGIHhtbG5zOnJkZj0iaHR0cDovL3d3dy53My5vcmcvMTk5OS8wMi8yMi1yZGYtc3ludGF4LW5zIyI+IDxyZGY6RGVzY3JpcHRpb24gcmRmOmFib3V0PSIiIHhtbG5zOnhtcD0iaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wLyIgeG1sbnM6eG1wTU09Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9tbS8iIHhtbG5zOnN0UmVmPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvc1R5cGUvUmVzb3VyY2VSZWYjIiB4bXA6Q3JlYXRvclRvb2w9IkFkb2JlIFBob3Rvc2hvcCAyNC4xIChNYWNpbnRvc2gpIiB4bXBNTTpJbnN0YW5jZUlEPSJ4bXAuaWlkOjlDN0Y5QzBDNEIxRDExRUU5MjgwQUNGNjU1QzlDQjREIiB4bXBNTTpEb2N1bWVudElEPSJ4bXAuZGlkOjlDN0Y5QzBENEIxRDExRUU5MjgwQUNGNjU1QzlDQjREIj4gPHhtcE1NOkRlcml2ZWRGcm9tIHN0UmVmOmluc3RhbmNlSUQ9InhtcC5paWQ6OUM3RjlDMEE0QjFEMTFFRTkyODBBQ0Y2NTVDOUNCNEQiIHN0UmVmOmRvY3VtZW50SUQ9InhtcC5kaWQ6OUM3RjlDMEI0QjFEMTFFRTkyODBBQ0Y2NTVDOUNCNEQiLz4gPC9yZGY6RGVzY3JpcHRpb24+IDwvcmRmOlJERj4gPC94OnhtcG1ldGE+IDw/eHBhY2tldCBlbmQ9InIiPz7/7gAOQWRvYmUAZMAAAAAB/9sAhAABAQEBAQEBAQEBAQEB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)"]},{"cell_type":"markdown","metadata":{"id":"LERqQn5v8-ak"},"source":["# **Getting to know Llama 2: Everything you need to start building**\n","Our goal in this session is to provide a guided tour of Llama 2, including understanding different Llama 2 models, how and where to access them, Generative AI and Chatbot architectures, prompt engineering, RAG (Retrieval Augmented Generation), Fine-tuning and more. All this is implemented with a starter code for you to take it and use it in your Llama 2 projects."]},{"cell_type":"markdown","metadata":{"id":"ioVMNcTesSEk"},"source":["##**0 - Prerequisites**\n","* Basic understanding of Large Language Models\n","\n","* Basic understanding of Python"]},{"cell_type":"code","execution_count":5,"metadata":{},"outputs":[{"name":"stdout","output_type":"stream","text":["Requirement already satisfied: matplotlib in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (3.8.0)\n","Requirement already satisfied: contourpy>=1.0.1 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (1.1.1)\n","Requirement already satisfied: cycler>=0.10 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (0.11.0)\n","Requirement already satisfied: fonttools>=4.22.0 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (4.42.1)\n","Requirement already satisfied: kiwisolver>=1.0.1 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (1.4.5)\n","Requirement already satisfied: numpy<2,>=1.21 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (1.25.2)\n","Requirement already satisfied: packaging>=20.0 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (23.1)\n","Requirement already satisfied: pillow>=6.2.0 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (9.3.0)\n","Requirement already satisfied: pyparsing>=2.3.1 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (3.1.1)\n","Requirement already satisfied: python-dateutil>=2.7 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from matplotlib) (2.8.2)\n","Requirement already satisfied: six>=1.5 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from python-dateutil>=2.7->matplotlib) (1.16.0)\n","Note: you may need to restart the kernel to use updated packages.\n","Collecting ipywidgets\n","  Obtaining dependency information for ipywidgets from https://files.pythonhosted.org/packages/4a/0e/57ed498fafbc60419a9332d872e929879ceba2d73cb11d284d7112472b3e/ipywidgets-8.1.1-py3-none-any.whl.metadata\n","  Downloading ipywidgets-8.1.1-py3-none-any.whl.metadata (2.4 kB)\n","Requirement already satisfied: comm>=0.1.3 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipywidgets) (0.1.4)\n","Requirement already satisfied: ipython>=6.1.0 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipywidgets) (8.15.0)\n","Requirement already satisfied: traitlets>=4.3.1 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipywidgets) (5.10.0)\n","Collecting widgetsnbextension~=4.0.9 (from ipywidgets)\n","  Obtaining dependency information for widgetsnbextension~=4.0.9 from https://files.pythonhosted.org/packages/29/03/107d96077c4befed191f7ad1a12c7b52a8f9d2778a5836d59f9855c105f6/widgetsnbextension-4.0.9-py3-none-any.whl.metadata\n","  Downloading widgetsnbextension-4.0.9-py3-none-any.whl.metadata (1.6 kB)\n","Collecting jupyterlab-widgets~=3.0.9 (from ipywidgets)\n","  Obtaining dependency information for jupyterlab-widgets~=3.0.9 from https://files.pythonhosted.org/packages/e8/05/0ebab152288693b5ec7b339aab857362947031143b282853b4c2dd4b5b40/jupyterlab_widgets-3.0.9-py3-none-any.whl.metadata\n","  Downloading jupyterlab_widgets-3.0.9-py3-none-any.whl.metadata (4.1 kB)\n","Requirement already satisfied: backcall in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (0.2.0)\n","Requirement already satisfied: decorator in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (5.1.1)\n","Requirement already satisfied: jedi>=0.16 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (0.19.0)\n","Requirement already satisfied: matplotlib-inline in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (0.1.6)\n","Requirement already satisfied: pickleshare in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (0.7.5)\n","Requirement already satisfied: prompt-toolkit!=3.0.37,<3.1.0,>=3.0.30 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (3.0.39)\n","Requirement already satisfied: pygments>=2.4.0 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (2.16.1)\n","Requirement already satisfied: stack-data in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (0.6.2)\n","Requirement already satisfied: exceptiongroup in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (1.1.3)\n","Requirement already satisfied: pexpect>4.3 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from ipython>=6.1.0->ipywidgets) (4.8.0)\n","Requirement already satisfied: parso<0.9.0,>=0.8.3 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from jedi>=0.16->ipython>=6.1.0->ipywidgets) (0.8.3)\n","Requirement already satisfied: ptyprocess>=0.5 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from pexpect>4.3->ipython>=6.1.0->ipywidgets) (0.7.0)\n","Requirement already satisfied: wcwidth in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from prompt-toolkit!=3.0.37,<3.1.0,>=3.0.30->ipython>=6.1.0->ipywidgets) (0.2.6)\n","Requirement already satisfied: executing>=1.2.0 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from stack-data->ipython>=6.1.0->ipywidgets) (1.2.0)\n","Requirement already satisfied: asttokens>=2.1.0 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from stack-data->ipython>=6.1.0->ipywidgets) (2.4.0)\n","Requirement already satisfied: pure-eval in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from stack-data->ipython>=6.1.0->ipywidgets) (0.2.2)\n","Requirement already satisfied: six>=1.12.0 in /data/home/hamidnazeri/miniconda/envs/llama-package/lib/python3.10/site-packages (from asttokens>=2.1.0->stack-data->ipython>=6.1.0->ipywidgets) (1.16.0)\n","Downloading ipywidgets-8.1.1-py3-none-any.whl (139 kB)\n","\u001b[2K   \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m139.4/139.4 kB\u001b[0m \u001b[31m2.5 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0mta \u001b[36m0:00:01\u001b[0m\n","\u001b[?25hDownloading jupyterlab_widgets-3.0.9-py3-none-any.whl (214 kB)\n","\u001b[2K   \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m214.9/214.9 kB\u001b[0m \u001b[31m5.2 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0mta \u001b[36m0:00:01\u001b[0m\n","\u001b[?25hDownloading widgetsnbextension-4.0.9-py3-none-any.whl (2.3 MB)\n","\u001b[2K   \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m2.3/2.3 MB\u001b[0m \u001b[31m24.0 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0m:00:01\u001b[0m\n","\u001b[?25hInstalling collected packages: widgetsnbextension, jupyterlab-widgets, ipywidgets\n","Successfully installed ipywidgets-8.1.1 jupyterlab-widgets-3.0.9 widgetsnbextension-4.0.9\n","Note: you may need to restart the kernel to use updated packages.\n"]}],"source":["%pip install matplotlib\n","%pip install ipywidgets"]},{"cell_type":"code","execution_count":6,"metadata":{"id":"ktEA7qXmwdUM"},"outputs":[],"source":["# presentation layer code\n","\n","import base64\n","from IPython.display import Image, display\n","import matplotlib.pyplot as plt\n","import ipywidgets as widgets\n","from IPython.display import display, Markdown\n","\n","\n","def mm(graph):\n","  graphbytes = graph.encode(\"ascii\")\n","  base64_bytes = base64.b64encode(graphbytes)\n","  base64_string = base64_bytes.decode(\"ascii\")\n","  display(Image(url=\"https://mermaid.ink/img/\" + base64_string))\n","\n","def genai_app_arch():\n","  mm(\"\"\"\n","  flowchart TD\n","    A[Users] --> B(Applications e.g. mobile, web)\n","    B --> |Hosted API|C(Platforms e.g. Custom, HuggingFace, Replicate)\n","    B -- optional --> E(Frameworks e.g. LangChain)\n","    C-->|User Input|D[Llama 2]\n","    D-->|Model Output|C\n","    E --> C\n","    classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def rag_arch():\n","  mm(\"\"\"\n","  flowchart TD\n","    A[User Prompts] --> B(Frameworks e.g. LangChain)\n","    B <--> |Database, Docs, XLS|C[fa:fa-database External Data]\n","    B -->|API|D[Llama 2]\n","    classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def llama2_family():\n","  mm(\"\"\"\n","  graph LR;\n","      llama-2 --> llama-2-7b\n","      llama-2 --> llama-2-13b\n","      llama-2 --> llama-2-70b\n","      llama-2-7b --> llama-2-7b-chat\n","      llama-2-13b --> llama-2-13b-chat\n","      llama-2-70b --> llama-2-70b-chat\n","      classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def apps_and_llms():\n","  mm(\"\"\"\n","  graph LR;\n","    users --> apps\n","    apps --> frameworks\n","    frameworks --> platforms\n","    platforms --> Llama 2\n","    classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","\n","\n","# Create a text widget\n","API_KEY = widgets.Password(\n","    value='',\n","    placeholder='',\n","    description='API_KEY:',\n","    disabled=False\n",")\n","\n","def md(t):\n","  display(Markdown(t))\n","\n","def bot_arch():\n","  mm(\"\"\"\n","  graph LR;\n","  user --> prompt\n","  prompt --> i_safety\n","  i_safety --> context\n","  context --> Llama_2\n","  Llama_2 --> output\n","  output --> o_safety\n","  i_safety --> memory\n","  o_safety --> memory\n","  memory --> context\n","  o_safety --> user\n","  classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def fine_tuned_arch():\n","  mm(\"\"\"\n","  graph LR;\n","      Custom_Dataset --> Pre-trained_Llama\n","      Pre-trained_Llama --> Fine-tuned_Llama\n","      Fine-tuned_Llama --> RLHF\n","      RLHF --> |Loss:Cross-Entropy|Fine-tuned_Llama\n","      classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def load_data_faiss_arch():\n","  mm(\"\"\"\n","  graph LR;\n","      documents --> textsplitter\n","      textsplitter --> embeddings\n","      embeddings --> vectorstore\n","      classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n","\n","def mem_context():\n","  mm(\"\"\"\n","      graph LR\n","      context(text)\n","      user_prompt --> context\n","      instruction --> context\n","      examples --> context\n","      memory --> context\n","      context --> tokenizer\n","      tokenizer --> embeddings\n","      embeddings --> LLM\n","      classDef default fill:#CCE6FF,stroke:#84BCF5,textColor:#1C2B33,fontFamily:trebuchet ms;\n","  \"\"\")\n"]},{"cell_type":"markdown","metadata":{"id":"i4Np_l_KtIno"},"source":["## **1 - Understanding Llama 2**"]},{"cell_type":"markdown","metadata":{"id":"PGPSI3M5PGTi"},"source":["### **1.1 - What is Llama 2?**\n","\n","* State of the art (SOTA), Open Source LLM\n","* 7B, 13B, 70B\n","* Pretrained + Chat\n","* Choosing model: Size, Quality, Cost, Speed\n","* [Research paper](https://ai.meta.com/research/publications/llama-2-open-foundation-and-fine-tuned-chat-models/)\n","\n","* [Responsible use guide](https://ai.meta.com/llama/responsible-use-guide/)"]},{"cell_type":"code","execution_count":7,"metadata":{"id":"OXRCC7wexZXd"},"outputs":[{"data":{"text/html":["<img src=\"https://mermaid.ink/img/CiAgZ3JhcGggTFI7CiAgICAgIGxsYW1hLTIgLS0+IGxsYW1hLTItN2IKICAgICAgbGxhbWEtMiAtLT4gbGxhbWEtMi0xM2IKICAgICAgbGxhbWEtMiAtLT4gbGxhbWEtMi03MGIKICAgICAgbGxhbWEtMi03YiAtLT4gbGxhbWEtMi03Yi1jaGF0CiAgICAgIGxsYW1hLTItMTNiIC0tPiBsbGFtYS0yLTEzYi1jaGF0CiAgICAgIGxsYW1hLTItNzBiIC0tPiBsbGFtYS0yLTcwYi1jaGF0CiAgICAgIGNsYXNzRGVmIGRlZmF1bHQgZmlsbDojQ0NFNkZGLHN0cm9rZTojODRCQ0Y1LHRleHRDb2xvcjojMUMyQjMzLGZvbnRGYW1pbHk6dHJlYnVjaGV0IG1zOwogIA==\"/>"],"text/plain":["<IPython.core.display.Image object>"]},"metadata":{},"output_type":"display_data"}],"source":["llama2_family()"]},{"cell_type":"markdown","metadata":{"id":"aYeHVVh45bdT"},"source":["### **1.2 - Accessing Llama 2**\n","* Download + Self Host (on-premise)\n","* Hosted API Platform (e.g. Replicate)\n","\n","* Hosted Container Platform (e.g. Azure, AWS, GCP)\n","\n"]},{"cell_type":"markdown","metadata":{"id":"kBuSay8vtzL4"},"source":["### **1.3 - Use Cases of Llama 2**\n","* Content Generation\n","* Chatbots\n","* Summarization\n","* Programming (e.g. Code Llama)\n","\n","* and many more..."]},{"cell_type":"markdown","metadata":{"id":"sd54g0OHuqBY"},"source":["## **2 - Using Llama 2**"]},{"cell_type":"markdown","metadata":{"id":"h3YGMDJidHtH"},"source":["### **2.1 - Install dependencies**"]},{"cell_type":"code","execution_count":8,"metadata":{"id":"VhN6hXwx7FCp"},"outputs":[{"name":"stdout","output_type":"stream","text":["Note: you may need to restart the kernel to use updated packages.\n"]}],"source":["# Install dependencies and initialize\n","%pip install -qU \\\n","    replicate \\\n","    langchain \\\n","    sentence_transformers \\\n","    pdf2image \\\n","    pdfminer \\\n","    pdfminer.six \\\n","    unstructured \\\n","    faiss-gpu"]},{"cell_type":"code","execution_count":9,"metadata":{"id":"Z8Y8qjEjmg50"},"outputs":[],"source":["# model we will use throughout the notebook\n","llama2_13b = \"meta/llama-2-13b-chat:f4e2de70d66816a838a89eeeb621910adffb0dd0baba3976c96980970978018d\""]},{"cell_type":"code","execution_count":13,"metadata":{"id":"8hkWpqWD28ho"},"outputs":[],"source":["# We will use Replicate hosted cloud environment\n","# Obtain Replicate API key → https://replicate.com/account/api-tokens)\n","# Find the model to use → we will use [`llama-2-13b-chat`](https://replicate.com/lucataco/llama-2-13b-chat)\n","\n","# enter your replicate api token\n","from getpass import getpass\n","import os\n","\n","REPLICATE_API_TOKEN = getpass()\n","REPLICATE_API_TOKEN  = \"r8_BllHLsEknCEcXvgyektqHMN4BrzOHe83CGxHz\"\n","os.environ[\"REPLICATE_API_TOKEN\"] = REPLICATE_API_TOKEN\n","\n","# alternatively, you can also store the tokens in environment variables and load it here"]},{"cell_type":"code","execution_count":11,"metadata":{"id":"bVCHZmETk36v"},"outputs":[],"source":["# we will use replicate's hosted api\n","import replicate\n","\n","# text completion with input prompt\n","def Completion(prompt):\n","  output = replicate.run(\n","      llama2_13b,\n","      input={\"prompt\": prompt, \"max_new_tokens\":1000}\n","  )\n","  return \"\".join(output)\n","\n","# chat completion with input prompt and system prompt\n","def ChatCompletion(prompt, system_prompt=None):\n","  output = replicate.run(\n","    llama2_13b,\n","    input={\"system_prompt\": system_prompt,\n","            \"prompt\": prompt,\n","            \"max_new_tokens\":1000}\n","  )\n","  return \"\".join(output)"]},{"cell_type":"markdown","metadata":{"id":"5Jxq0pmf6L73"},"source":["### **2.2 - Basic completion**"]},{"cell_type":"code","execution_count":12,"metadata":{"id":"H93zZBIk6tNU"},"outputs":[{"ename":"ReplicateError","evalue":"Incorrect authentication token. Learn how to authenticate and get your API token here: https://replicate.com/docs/reference/http#authentication","output_type":"error","traceback":["\u001b[0;31m---------------------------------------------------------------------------\u001b[0m","\u001b[0;31mReplicateError\u001b[0m                            Traceback (most recent call last)","\u001b[1;32m/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb Cell 18\u001b[0m line \u001b[0;36m1\n\u001b[0;32m----> <a href='vscode-notebook-cell://ssh-remote%2Bpytorch/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb#X22sdnNjb2RlLXJlbW90ZQ%3D%3D?line=0'>1</a>\u001b[0m output \u001b[39m=\u001b[39m Completion(prompt\u001b[39m=\u001b[39;49m\u001b[39m\"\u001b[39;49m\u001b[39mThe typical color of a llama is: \u001b[39;49m\u001b[39m\"\u001b[39;49m)\n\u001b[1;32m      <a href='vscode-notebook-cell://ssh-remote%2Bpytorch/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb#X22sdnNjb2RlLXJlbW90ZQ%3D%3D?line=1'>2</a>\u001b[0m md(output)\n","\u001b[1;32m/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb Cell 18\u001b[0m line \u001b[0;36m6\n\u001b[1;32m      <a href='vscode-notebook-cell://ssh-remote%2Bpytorch/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb#X22sdnNjb2RlLXJlbW90ZQ%3D%3D?line=4'>5</a>\u001b[0m \u001b[39mdef\u001b[39;00m \u001b[39mCompletion\u001b[39m(prompt):\n\u001b[0;32m----> <a href='vscode-notebook-cell://ssh-remote%2Bpytorch/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb#X22sdnNjb2RlLXJlbW90ZQ%3D%3D?line=5'>6</a>\u001b[0m   output \u001b[39m=\u001b[39m replicate\u001b[39m.\u001b[39;49mrun(\n\u001b[1;32m      <a href='vscode-notebook-cell://ssh-remote%2Bpytorch/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb#X22sdnNjb2RlLXJlbW90ZQ%3D%3D?line=6'>7</a>\u001b[0m       llama2_13b,\n\u001b[1;32m      <a href='vscode-notebook-cell://ssh-remote%2Bpytorch/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb#X22sdnNjb2RlLXJlbW90ZQ%3D%3D?line=7'>8</a>\u001b[0m       \u001b[39minput\u001b[39;49m\u001b[39m=\u001b[39;49m{\u001b[39m\"\u001b[39;49m\u001b[39mprompt\u001b[39;49m\u001b[39m\"\u001b[39;49m: prompt, \u001b[39m\"\u001b[39;49m\u001b[39mmax_new_tokens\u001b[39;49m\u001b[39m\"\u001b[39;49m:\u001b[39m1000\u001b[39;49m}\n\u001b[1;32m      <a href='vscode-notebook-cell://ssh-remote%2Bpytorch/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb#X22sdnNjb2RlLXJlbW90ZQ%3D%3D?line=8'>9</a>\u001b[0m   )\n\u001b[1;32m     <a href='vscode-notebook-cell://ssh-remote%2Bpytorch/data/home/hamidnazeri/llama-package/llama-recipes/examples/Getting_to_know_Llama.ipynb#X22sdnNjb2RlLXJlbW90ZQ%3D%3D?line=9'>10</a>\u001b[0m   \u001b[39mreturn\u001b[39;00m \u001b[39m\"\u001b[39m\u001b[39m\"\u001b[39m\u001b[39m.\u001b[39mjoin(output)\n","File \u001b[0;32m~/miniconda/envs/llama-package/lib/python3.10/site-packages/replicate/client.py:138\u001b[0m, in \u001b[0;36mClient.run\u001b[0;34m(self, model_version, **kwargs)\u001b[0m\n\u001b[1;32m    134\u001b[0m     \u001b[39mraise\u001b[39;00m ReplicateError(\n\u001b[1;32m    135\u001b[0m         \u001b[39mf\u001b[39m\u001b[39m\"\u001b[39m\u001b[39mInvalid model_version: \u001b[39m\u001b[39m{\u001b[39;00mmodel_version\u001b[39m}\u001b[39;00m\u001b[39m. Expected format: owner/name:version\u001b[39m\u001b[39m\"\u001b[39m\n\u001b[1;32m    136\u001b[0m     )\n\u001b[1;32m    137\u001b[0m model \u001b[39m=\u001b[39m \u001b[39mself\u001b[39m\u001b[39m.\u001b[39mmodels\u001b[39m.\u001b[39mget(m\u001b[39m.\u001b[39mgroup(\u001b[39m\"\u001b[39m\u001b[39mmodel\u001b[39m\u001b[39m\"\u001b[39m))\n\u001b[0;32m--> 138\u001b[0m version \u001b[39m=\u001b[39m model\u001b[39m.\u001b[39;49mversions\u001b[39m.\u001b[39;49mget(m\u001b[39m.\u001b[39;49mgroup(\u001b[39m\"\u001b[39;49m\u001b[39mversion\u001b[39;49m\u001b[39m\"\u001b[39;49m))\n\u001b[1;32m    139\u001b[0m prediction \u001b[39m=\u001b[39m \u001b[39mself\u001b[39m\u001b[39m.\u001b[39mpredictions\u001b[39m.\u001b[39mcreate(version\u001b[39m=\u001b[39mversion, \u001b[39m*\u001b[39m\u001b[39m*\u001b[39mkwargs)\n\u001b[1;32m    140\u001b[0m \u001b[39m# Return an iterator of the output\u001b[39;00m\n","File \u001b[0;32m~/miniconda/envs/llama-package/lib/python3.10/site-packages/replicate/version.py:89\u001b[0m, in \u001b[0;36mVersionCollection.get\u001b[0;34m(self, id)\u001b[0m\n\u001b[1;32m     80\u001b[0m \u001b[39mdef\u001b[39;00m \u001b[39mget\u001b[39m(\u001b[39mself\u001b[39m, \u001b[39mid\u001b[39m: \u001b[39mstr\u001b[39m) \u001b[39m-\u001b[39m\u001b[39m>\u001b[39m Version:\n\u001b[1;32m     81\u001b[0m \u001b[39m    \u001b[39m\u001b[39m\"\"\"\u001b[39;00m\n\u001b[1;32m     82\u001b[0m \u001b[39m    Get a specific model version.\u001b[39;00m\n\u001b[1;32m     83\u001b[0m \n\u001b[0;32m   (...)\u001b[0m\n\u001b[1;32m     87\u001b[0m \u001b[39m        The model version.\u001b[39;00m\n\u001b[1;32m     88\u001b[0m \u001b[39m    \"\"\"\u001b[39;00m\n\u001b[0;32m---> 89\u001b[0m     resp \u001b[39m=\u001b[39m \u001b[39mself\u001b[39;49m\u001b[39m.\u001b[39;49m_client\u001b[39m.\u001b[39;49m_request(\n\u001b[1;32m     90\u001b[0m         \u001b[39m\"\u001b[39;49m\u001b[39mGET\u001b[39;49m\u001b[39m\"\u001b[39;49m, \u001b[39mf\u001b[39;49m\u001b[39m\"\u001b[39;49m\u001b[39m/v1/models/\u001b[39;49m\u001b[39m{\u001b[39;49;00m\u001b[39mself\u001b[39;49m\u001b[39m.\u001b[39;49m_model\u001b[39m.\u001b[39;49musername\u001b[39m}\u001b[39;49;00m\u001b[39m/\u001b[39;49m\u001b[39m{\u001b[39;49;00m\u001b[39mself\u001b[39;49m\u001b[39m.\u001b[39;49m_model\u001b[39m.\u001b[39;49mname\u001b[39m}\u001b[39;49;00m\u001b[39m/versions/\u001b[39;49m\u001b[39m{\u001b[39;49;00m\u001b[39mid\u001b[39;49m\u001b[39m}\u001b[39;49;00m\u001b[39m\"\u001b[39;49m\n\u001b[1;32m     91\u001b[0m     )\n\u001b[1;32m     92\u001b[0m     \u001b[39mreturn\u001b[39;00m \u001b[39mself\u001b[39m\u001b[39m.\u001b[39mprepare_model(resp\u001b[39m.\u001b[39mjson())\n","File \u001b[0;32m~/miniconda/envs/llama-package/lib/python3.10/site-packages/replicate/client.py:80\u001b[0m, in \u001b[0;36mClient._request\u001b[0;34m(self, method, path, **kwargs)\u001b[0m\n\u001b[1;32m     78\u001b[0m \u001b[39mif\u001b[39;00m \u001b[39m400\u001b[39m \u001b[39m<\u001b[39m\u001b[39m=\u001b[39m resp\u001b[39m.\u001b[39mstatus_code \u001b[39m<\u001b[39m \u001b[39m600\u001b[39m:\n\u001b[1;32m     79\u001b[0m     \u001b[39mtry\u001b[39;00m:\n\u001b[0;32m---> 80\u001b[0m         \u001b[39mraise\u001b[39;00m ReplicateError(resp\u001b[39m.\u001b[39mjson()[\u001b[39m\"\u001b[39m\u001b[39mdetail\u001b[39m\u001b[39m\"\u001b[39m])\n\u001b[1;32m     81\u001b[0m     \u001b[39mexcept\u001b[39;00m (JSONDecodeError, \u001b[39mKeyError\u001b[39;00m):\n\u001b[1;32m     82\u001b[0m         \u001b[39mpass\u001b[39;00m\n","\u001b[0;31mReplicateError\u001b[0m: Incorrect authentication token. Learn how to authenticate and get your API token here: https://replicate.com/docs/reference/http#authentication"]}],"source":["output = Completion(prompt=\"The typical color of a llama is: \")\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"StccjUDh6W0Q"},"source":["### **2.3 - System prompts**\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"VRnFogxd6rTc"},"outputs":[],"source":["output = ChatCompletion(\n","    prompt=\"The typical color of a llama is: \",\n","    system_prompt=\"respond with only one word\"\n","  )\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"Hp4GNa066pYy"},"source":["### **2.4 - Response formats**\n","* Can support different formatted outputs e.g. text, JSON, etc."]},{"cell_type":"code","execution_count":null,"metadata":{"id":"HTN79h4RptgQ"},"outputs":[],"source":["output = ChatCompletion(\n","    prompt=\"The typical color of a llama is: \",\n","    system_prompt=\"response in json format\"\n","  )\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"cWs_s9y-avIT"},"source":["## **3 - Gen AI Application Architecture**\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"j9BGuI-9AOL5"},"outputs":[],"source":["genai_app_arch()"]},{"cell_type":"markdown","metadata":{"id":"6UlxBtbgys6j"},"source":["##4 - **Chatbot Architecture**\n","* User Prompts\n","* Input Safety\n","* Llama 2\n","* Output Safety\n","\n","* Memory & Context"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"tO5HnB56ys6t"},"outputs":[],"source":["bot_arch()"]},{"cell_type":"markdown","metadata":{"id":"r4DyTLD5ys6t"},"source":["### **4.1 - Chat conversation**\n","* LLMs are stateless\n","* Single Turn\n","\n","* Multi Turn (Memory)\n","\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"EMM_egWMys6u"},"outputs":[],"source":["# example of single turn chat\n","prompt_chat = \"What is the average lifespan of a Llama?\"\n","output = ChatCompletion(prompt=prompt_chat, system_prompt=\"answer the last question in few words\")\n","md(output)"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"sZ7uVKDYucgi"},"outputs":[],"source":["# example without previous context. LLM's are stateless and cannot understand \"they\" without previous context\n","prompt_chat = \"What animal family are they?\"\n","output = ChatCompletion(prompt=prompt_chat, system_prompt=\"answer the last question in few words\")\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"WQl3wmfbyBQ1"},"source":["Chat app requires us to send in previous context to LLM to get in valid responses. Below is an example of Multi-turn chat."]},{"cell_type":"code","execution_count":null,"metadata":{"id":"t7SZe5fT3HG3"},"outputs":[],"source":["# example of multi-turn chat, with storing previous context\n","prompt_chat = \"\"\"\n","User: What is the average lifespan of a Llama?\n","Assistant: Sure! The average lifespan of a llama is around 20-30 years.\n","User: What animal family are they?\n","\"\"\"\n","output = ChatCompletion(prompt=prompt_chat, system_prompt=\"answer the last question\")\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"moXnmJ_xyD10"},"source":["### **4.2 - Prompt Engineering**\n","Prompt engineering refers to the science of designing effective prompts to get desired responses.\n"]},{"cell_type":"markdown","metadata":{"id":"t-v-FeZ4ztTB"},"source":["#### **4.2.1 - In-Context Learning (e.g. Zero-shot, Few-shot)**\n"," * In-context learning - specific method of prompt engineering where demonstration of task are provided as part of prompt.\n","  1. Zero-shot learning - model is performing tasks without any\n","input examples.\n","  2. Few or “N-Shot” Learning - model is performing and behaving based on input examples in user's prompt.\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"6W71MFNZyRkQ"},"outputs":[],"source":["# Zero-shot example. To get positive/negative/neutral sentiment, we need to give examples in the prompt\n","prompt = '''\n","Classify: I saw a Gecko.\n","Sentiment: ?\n","'''\n","output = ChatCompletion(prompt, system_prompt=\"one word response\")\n","md(output)"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"MCQRjf1Y1RYJ"},"outputs":[],"source":["# By giving examples to Llama, it understands the expected output format.\n","\n","prompt = '''\n","Classify: I love Llamas!\n","Sentiment: Positive\n","Classify: I dont like Snakes.\n","Sentiment: Negative\n","Classify: I saw a Gecko.\n","Sentiment:'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"One word response\")\n","md(output)"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"8UmdlTmpDZxA"},"outputs":[],"source":["# another zero-shot learning\n","prompt = '''\n","QUESTION: Vicuna?\n","ANSWER:'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"one word response\")\n","md(output)"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"M_EcsUo1zqFD"},"outputs":[],"source":["# Another few-shot learning example with formatted prompt.\n","\n","prompt = '''\n","QUESTION: Llama?\n","ANSWER: Yes\n","QUESTION: Alpaca?\n","ANSWER: Yes\n","QUESTION: Rabbit?\n","ANSWER: No\n","QUESTION: Vicuna?\n","ANSWER:'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"one word response\")\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"mbr124Y197xl"},"source":["#### **4.2.2 - Chain of Thought**\n","* \"chain of thought\" or a coherent sequence of ideas is crucial for generating meaningful and contextually relevant responses\n","\n","* Hallucination on word problems"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"Xn8zmLBQzpgj"},"outputs":[],"source":["# Standard prompting\n","prompt = '''\n","Llama started with 5 tennis balls. It buys 2 more cans of tennis balls. Each can has 3 tennis balls. How many tennis balls does Llama have now?\n","'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"provide short answer\")\n","md(output)"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"lKNOj79o1Kwu"},"outputs":[],"source":["# Chain-Of-Thought prompting\n","prompt = '''\n","Llama started with 5 tennis balls. It buys 2 more cans of tennis balls. Each can has 3 tennis balls. How many tennis balls does Llama have now?\n","Let's think step by step.\n","'''\n","\n","output = ChatCompletion(prompt, system_prompt=\"provide short answer\")\n","md(output)"]},{"cell_type":"markdown","metadata":{"id":"C7tDW-AH770Y"},"source":["### **4.3 - Retrieval Augmented Generation (RAG)**\n","* Prompt Eng Limitations (Knowledge cutoff & lack of specialized data)\n","\n","* Langchain\n","\n","Retrieval Augmented Generation(RAG) allows us to retrieve snippets of information from external data sources and augment it to the user's prompt to get tailored responses from Llama 2.\n","\n","\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"Fl1LPltpRQD9"},"outputs":[],"source":["rag_arch()"]},{"cell_type":"markdown","metadata":{"id":"JJaGMLl_4vYm"},"source":["#### **4.3.1 - LangChain**\n","LangChain is a framework that helps make it easier to implement RAG.\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"aoqU3KTcHTWN"},"outputs":[],"source":["# langchain setup\n","from langchain.llms import Replicate\n","# Use the Llama 2 model hosted on Replicate\n","# Temperature: Adjusts randomness of outputs, greater than 1 is random and 0 is deterministic, 0.75 is a good starting value\n","# top_p: When decoding text, samples from the top p percentage of most likely tokens; lower to ignore less likely tokens\n","# max_new_tokens: Maximum number of tokens to generate. A word is generally 2-3 tokens\n","llama_model = Replicate(\n","    model=llama2_13b,\n","    model_kwargs={\"temperature\": 0.75,\"top_p\": 1, \"max_new_tokens\":1000}\n",")"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"gAV2EkZqcruF"},"outputs":[],"source":["# Step 1: load the external data source. In our case, we will load Meta’s “Responsible Use Guide” pdf document.\n","from langchain.document_loaders import OnlinePDFLoader\n","loader = OnlinePDFLoader(\"https://ai.meta.com/static-resource/responsible-use-guide/\")\n","documents = loader.load()\n","\n","# Step 2: Get text splits from document\n","from langchain.text_splitter import RecursiveCharacterTextSplitter\n","text_splitter = RecursiveCharacterTextSplitter(chunk_size=1000, chunk_overlap=20)\n","all_splits = text_splitter.split_documents(documents)\n","\n","# Step 3: Use the embedding model\n","from langchain.vectorstores import FAISS\n","from langchain.embeddings import HuggingFaceEmbeddings\n","model_name = \"sentence-transformers/all-mpnet-base-v2\" # embedding model\n","model_kwargs = {\"device\": \"cpu\"}\n","embeddings = HuggingFaceEmbeddings(model_name=model_name, model_kwargs=model_kwargs)\n","\n","# Step 4: Use vector store to store embeddings\n","vectorstore = FAISS.from_documents(all_splits, embeddings)"]},{"cell_type":"markdown","metadata":{"id":"K2l8S5tBxlkc"},"source":["#### **4.3.2 - LangChain Q&A Retriever**\n","* ConversationalRetrievalChain\n","\n","* Query the Source documents\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"NmEhBe3Kiyre"},"outputs":[],"source":["# Query against your own data\n","from langchain.chains import ConversationalRetrievalChain\n","chain = ConversationalRetrievalChain.from_llm(llama_model, vectorstore.as_retriever(), return_source_documents=True)\n","\n","chat_history = []\n","query = \"How is Meta approaching open science in two short sentences?\"\n","result = chain({\"question\": query, \"chat_history\": chat_history})\n","md(result['answer'])"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"CelLHIvoy2Ke"},"outputs":[],"source":["# This time your previous question and answer will be included as a chat history which will enable the ability\n","# to ask follow up questions.\n","chat_history = [(query, result[\"answer\"])]\n","query = \"How is it benefiting the world?\"\n","result = chain({\"question\": query, \"chat_history\": chat_history})\n","md(result['answer'])"]},{"cell_type":"markdown","metadata":{"id":"TEvefAWIJONx"},"source":["## **5 - Fine-Tuning Models**\n","\n","* Limitatons of Prompt Eng and RAG\n","* Fine-Tuning Arch\n","* Types (PEFT, LoRA, QLoRA)\n","* Using PyTorch for Pre-Training & Fine-Tuning\n","\n","* Evals + Quality\n"]},{"cell_type":"code","execution_count":null,"metadata":{"id":"0a9CvJ8YcTzV"},"outputs":[],"source":["fine_tuned_arch()"]},{"cell_type":"markdown","metadata":{"id":"_8lcgdZa8onC"},"source":["## **6 - Responsible AI**\n","\n","* Power + Responsibility\n","* Hallucinations\n","* Input & Output Safety\n","* Red-teaming (simulating real-world cyber attackers)\n","* [Responsible Use Guide](https://ai.meta.com/llama/responsible-use-guide/)\n","\n"]},{"cell_type":"markdown","metadata":{"id":"pbqb006R-T_k"},"source":["##**7 - Conclusion**\n","* Active research on LLMs and Llama\n","* Leverage the power of Llama and its open community\n","* Safety and responsible use is paramount!\n","\n","* Call-To-Action\n","  * [Replicate Free Credits](https://replicate.fyi/connect2023) for Connect attendees!\n","  * This notebook is available through Llama Github recipes\n","  * Use Llama in your projects and give us feedback\n"]},{"cell_type":"markdown","metadata":{"id":"gSz5dTMxp7xo"},"source":["#### **Resources**\n","- [GitHub - Llama 2](https://github.com/facebookresearch/llama)\n","- [Github - LLama 2 Recipes](https://github.com/facebookresearch/llama-recipes)\n","- [Llama 2](https://ai.meta.com/llama/)\n","- [Research Paper](https://ai.meta.com/research/publications/llama-2-open-foundation-and-fine-tuned-chat-models/)\n","- [Model Card](https://github.com/facebookresearch/llama/blob/main/MODEL_CARD.md)\n","- [Responsible Use Guide](https://ai.meta.com/llama/responsible-use-guide/)\n","- [Acceptable Use Policy](https://ai.meta.com/llama/use-policy/)\n","- [Replicate](https://replicate.com/meta/)\n","- [LangChain](https://www.langchain.com/)\n","\n"]},{"cell_type":"markdown","metadata":{"id":"V7aI6fhZp-KC"},"source":["#### **Authors & Contact**\n","  * asangani@meta.com, [Amit Sangani | LinkedIn](https://www.linkedin.com/in/amitsangani/)\n","  * mohsena@meta.com, [Mohsen Agsen | LinkedIn](https://www.linkedin.com/in/mohsen-agsen-62a9791/)\n"]}],"metadata":{"colab":{"collapsed_sections":["ioVMNcTesSEk"],"machine_shape":"hm","provenance":[],"toc_visible":true},"kernelspec":{"display_name":"Python 3","name":"python3"},"language_info":{"codemirror_mode":{"name":"ipython","version":3},"file_extension":".py","mimetype":"text/x-python","name":"python","nbconvert_exporter":"python","pygments_lexer":"ipython3","version":"3.10.13"}},"nbformat":4,"nbformat_minor":0}