Repository: wombyz/HormoziGPT
Branch: main
Commit: 781f775d8201
Files: 9
Total size: 12.8 KB
Directory structure:
gitextract_ixh5zxzz/
├── .gitignore
├── .streamlit/
│ └── config.toml
├── CONTRIBUTING.md
├── README.md
├── app.py
├── prompts.py
├── render.py
├── requirements.txt
└── utils.py
================================================
FILE CONTENTS
================================================
================================================
FILE: .gitignore
================================================
.env
/.streamlit/secrets.toml
================================================
FILE: .streamlit/config.toml
================================================
[theme]
primaryColor="#F63366"
backgroundColor="#FFFFFF"
secondaryBackgroundColor="#F0F2F6"
textColor="#262730"
font="sans serif"
================================================
FILE: CONTRIBUTING.md
================================================
# Contributing to HormoziGPT
First of all, thank you for considering contributing to HormoziGPT! I made this project as an experiment in creating artificial personalities based on existing content, so I appreciate any help and contributions from the community. Whether you're submitting a bug report, suggesting a new feature, or contributing code, your contributions are valuable and help improve the project.
## How to Contribute
### Reporting Bugs
If you encounter any bugs or issues while using HormoziGPT, please open an issue on the GitHub repository. When submitting a bug report, please include the following information:
- A clear and descriptive title for the issue.
- A detailed description of the issue, including steps to reproduce it.
- Information about your environment, such as the operating system and Python version you're using.
### Suggesting Enhancements
If you have an idea for a new feature or enhancement, please open an issue on the GitHub repository. When suggesting an enhancement, please include the following information:
- A clear and descriptive title for the issue.
- A detailed description of the proposed enhancement, including any benefits and potential use cases.
- Any relevant examples or mockups, if applicable.
### Contributing Code
If you'd like to contribute code to HormoziGPT, please follow these steps:
1. Fork the HormoziGPT repository on GitHub.
2. Clone your fork to your local machine.
3. Create a new branch for your changes (e.g., `git checkout -b my-feature-branch`).
4. Make your changes and commit them to your branch.
5. Push your changes to your fork on GitHub.
6. Open a pull request against the `main` branch of the HormoziGPT repository.
When submitting a pull request, please include a clear and descriptive title and a detailed description of your changes. If your pull request addresses an existing issue, please reference the issue number in the description.
## Code of Conduct
I strive to create a welcoming and inclusive environment for all contributors. Please be respectful and considerate in your interactions with others.
## Contact
If you have any questions or need assistance, please feel free to reach out to me directly. You can contact me via [GitHub](https://github.com/wombyz) or [email](mailto:admin@liamottley.com).
Thank you again for your interest in contributing to HormoziGPT, and I look forward to collaborating with you!
================================================
FILE: README.md
================================================
# HormoziGPT
HormoziGPT is a chatbot application that simulates a conversation with Alex Hormozi. The chatbot provides valuable business advice and coaching to users, drawing from Alex's experience in customer acquisition, monetization, and scaling businesses. It also has access to transcripts of Alex's podcasts, which are used to provide context and support for the chatbot's responses.
## Features
- Engage in a conversation with a chatbot that emulates Alex Hormozi's communication style.
- Receive focused, practical, and direct business advice.
- Access relevant snippets from transcripts of Alex's podcasts to support the chatbot's responses.
- Utilize semantic search to find relevant content from the transcripts.
## Getting Started
### Prerequisites
- Python 3.7 or higher
- OpenAI API key
- Pinecone API key and environment details
### Installation
1. Clone the repository:
```
git clone https://github.com/your-repo-url/HormoziGPT.git
```
2. Change to the project directory:
```
cd HormoziGPT
```
3. Install the required dependencies:
```
pip install -r requirements.txt
```
4. Set up the environment variables:
- `OPENAI_API_KEY`: Your OpenAI API key
- `PINECONE_API_KEY`: Your Pinecone API key
- `PINECONE_ENVIRONMENT`: Your Pinecone environment details
- `PINECONE_ENDPOINT`: Your Pinecone endpoint
### Usage
1. Run the Streamlit app:
```
streamlit run app.py
```
2. Open the app in your web browser and enter your prompt to start the conversation with the chatbot.
## Contributing
Contributions are welcome! Please read the [CONTRIBUTING.md](CONTRIBUTING.md) file for details on how to contribute to the project.
## Acknowledgments
- Alex Hormozi for his valuable insights and business advice! (don't sue me)
- OpenAI for their language models and embeddings.
- Pinecone for their semantic search capabilities.
================================================
FILE: app.py
================================================
import os
import openai
import streamlit as st
from dotenv import load_dotenv
from render import bot_msg_container_html_template, user_msg_container_html_template
from utils import semantic_search
import prompts
import pinecone
# Set up OpenAI API key
openai.api_key = st.secrets["OPENAI_API_KEY"]
pinecone.init(api_key=st.secrets["PINECONE_API_KEY"], environment=st.secrets["PINECONE_ENVIRONMENT"])
index = pinecone.Index(st.secrets["PINECONE_INDEX_NAME"])
st.header("HormoziGPT - By Liam Ottley")
# Define chat history storage
if "history" not in st.session_state:
st.session_state.history = []
# Construct messages from chat history
def construct_messages(history):
messages = [{"role": "system", "content": prompts.system_message}]
for entry in history:
role = "user" if entry["is_user"] else "assistant"
messages.append({"role": role, "content": entry["message"]})
return messages
# Generate response to user prompt
def generate_response():
st.session_state.history.append({
"message": st.session_state.prompt,
"is_user": True
})
print(f"Query: {st.session_state.prompt}")
# Perform semantic search and format results
search_results = semantic_search(st.session_state.prompt, index, top_k=3)
print(f"Results: {search_results}")
context = ""
for i, (title, transcript) in enumerate(search_results):
context += f"Snippet from: {title}\n {transcript}\n\n"
# Generate human prompt template and convert to API message format
query_with_context = prompts.human_template.format(query=st.session_state.prompt, context=context)
# Convert chat history to a list of messages
messages = construct_messages(st.session_state.history)
messages.append({"role": "user", "content": query_with_context})
# Run the LLMChain
response = openai.ChatCompletion.create(model="gpt-3.5-turbo", messages=messages)
print(messages)
# Parse response
bot_response = response["choices"][0]["message"]["content"]
st.session_state.history.append({
"message": bot_response,
"is_user": False
})
# User input prompt
user_prompt = st.text_input("Enter your prompt:",
key="prompt",
placeholder="e.g. 'Write me a business plan to scale my coaching business'",
on_change=generate_response
)
# Display chat history
for message in st.session_state.history:
if message["is_user"]:
st.write(user_msg_container_html_template.replace("$MSG", message["message"]), unsafe_allow_html=True)
else:
st.write(bot_msg_container_html_template.replace("$MSG", message["message"]), unsafe_allow_html=True)
================================================
FILE: prompts.py
================================================
system_message = """
You are Alex Hormozi, a successful entrepreneur and investor known for your no-nonsense approach to business advice. You have founded and scaled multiple companies, and you have a wealth of experience in customer acquisition, monetization, and scaling businesses.
Your goal is to provide valuable business advice and coaching to users. Your responses should be focused, practical, and direct, mirroring your own communication style. Avoid sugarcoating or beating around the bush—users expect you to be straightforward and honest.
You have access to transcripts of your own podcasts stored in a Pinecone database. These transcripts contain your actual words, ideas, and beliefs. When a user provides a query, you will be provided with snippets of transcripts that may be relevant to the query. You must use these snippets to provide context and support for your responses. Rely heavily on the content of the transcripts to ensure accuracy and authenticity in your answers.
Be aware that the transcripts may not always be relevant to the query. Analyze each of them carefully to determine if the content is relevant before using them to construct your answer. Do not make things up or provide information that is not supported by the transcripts.
In addition to offering business advice, you may also provide guidance on personal development and navigating the challenges of entrepreneurship. However, always maintain your signature no-bullshit approach.
Your goal is to provide advice that is as close as possible to what the real Alex Hormozi would say.
DO NOT make any reference to the snippets or the transcripts in your responses. You may use the snippets to provide context and support for your responses, but you should not mention them explicitly.
"""
human_template = """
User Query: {query}
Relevant Transcript Snippets: {context}
"""
================================================
FILE: render.py
================================================
import streamlit as st
import re
bot_msg_container_html_template = '''
<div style='background-color: #FFFFFF; padding: 10px; border-radius: 5px; margin-bottom: 10px; display: flex'>
<div style="width: 20%; display: flex; justify-content: center">
<img src="https://yt3.googleusercontent.com/ixwBtVrollE0Z5nA5YPHrnkKQoK09Evbe4gWCvJlleB2rFERDz3m2Jynhc3sGBE-EnzbH6ov=s176-c-k-c0x00ffffff-no-rj" style="max-height: 50px; max-width: 50px; border-radius: 50%;">
</div>
<div style="width: 80%;">
$MSG
</div>
</div>
'''
user_msg_container_html_template = '''
<div style='background-color: #FFFFFF; padding: 10px; border-radius: 5px; margin-bottom: 10px; display: flex'>
<div style="width: 78%">
$MSG
</div>
<div style="width: 20%; margin-left: auto; display: flex; justify-content: center;">
<img src="https://yt3.googleusercontent.com/w3Hwj4_weJ_tx9z79ffwCmaAU3eHPuJ5nvk_QDmNyxcbNdTaBBAIxenUXGybyUjLE4ktVKqyEA=s176-c-k-c0x00ffffff-no-rj" style="max-width: 50px; max-height: 50px; float: right; border-radius: 50%;">
</div>
</div>
'''
def render_article_preview(docs, tickers):
message = f"<h5>Here are relevant articles for {tickers} that may answer your question. </h5>"
message += "<div>"
for d in docs:
elipse = " ".join(d[2].split(" ")[:140])
message += f"<br><a href='{d[1]}'>{d[0]}</a></br>"
message += f"<p>{elipse} ...</p>"
message += "<br>"
message += "</div>"
return message
def render_earnings_summary(ticker, summary):
transcript_title = summary["transcript_title"]
message = f"<h5>Here is summary for {ticker} {transcript_title} </h5>"
message += "<div>"
body = re.sub(r'^-', r'* ', summary["summary"])
body = re.sub(r'\$', r'\\$', body)
message += f"<p>{body}</p>"
message += "</div>"
return message
def render_stock_question(answer, articles):
message = "<div>"
message += f"{answer} <br>"
message += "Sources: "
for a in articles:
message += f"<a href='{a[1]}'>{a[0]}</a><br>"
message += "</div>"
return message
def render_chat(**kwargs):
"""
Handles is_user
"""
if kwargs["is_user"]:
st.write(
user_msg_container_html_template.replace("$MSG", kwargs["message"]),
unsafe_allow_html=True)
else:
st.write(
bot_msg_container_html_template.replace("$MSG", kwargs["message"]),
unsafe_allow_html=True)
if "figs" in kwargs:
for f in kwargs["figs"]:
st.plotly_chart(f, use_container_width=True)
================================================
FILE: requirements.txt
================================================
streamlit==1.21.0
openai==0.27.4
requests==2.28.2
python-dotenv==1.0.0
pinecone-client==2.2.1
================================================
FILE: utils.py
================================================
import os
import openai
import requests
import streamlit as st
import json
openai.api_key = st.secrets["OPENAI_API_KEY"]
api_key_pinecone = st.secrets["PINECONE_API_KEY"]
pinecone_environment = st.secrets["PINECONE_ENVIRONMENT"]
pinecone_endpoint = st.secrets["PINECONE_ENDPOINT"]
def get_embeddings_openai(text):
try:
response = openai.Embedding.create(
input=text,
model="text-embedding-ada-002"
)
response = response['data']
return [x["embedding"] for x in response]
except Exception as e:
print(f"Error in get_embeddings_openai: {e}")
raise
def semantic_search(query, index, **kwargs):
try:
xq = get_embeddings_openai(query)
xr = index.query(vector=xq[0], top_k=kwargs.get('top_k', 1), include_metadata=kwargs.get('include_metadata', True))
if xr.error:
print(f"Invalid response: {xr}")
raise Exception(f"Query failed: {xr.error}")
titles = [r["metadata"]["title"] for r in xr["matches"]]
transcripts = [r["metadata"]["transcript"] for r in xr["matches"]]
return list(zip(titles, transcripts))
except Exception as e:
print(f"Error in semantic_search: {e}")
raise
gitextract_ixh5zxzz/ ├── .gitignore ├── .streamlit/ │ └── config.toml ├── CONTRIBUTING.md ├── README.md ├── app.py ├── prompts.py ├── render.py ├── requirements.txt └── utils.py
SYMBOL INDEX (8 symbols across 3 files) FILE: app.py function construct_messages (line 23) | def construct_messages(history): function generate_response (line 33) | def generate_response(): FILE: render.py function render_article_preview (line 27) | def render_article_preview(docs, tickers): function render_earnings_summary (line 38) | def render_earnings_summary(ticker, summary): function render_stock_question (line 48) | def render_stock_question(answer, articles): function render_chat (line 57) | def render_chat(**kwargs): FILE: utils.py function get_embeddings_openai (line 12) | def get_embeddings_openai(text): function semantic_search (line 24) | def semantic_search(query, index, **kwargs):
Condensed preview — 9 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (14K chars).
[
{
"path": ".gitignore",
"chars": 30,
"preview": ".env\n/.streamlit/secrets.toml\n"
},
{
"path": ".streamlit/config.toml",
"chars": 129,
"preview": "[theme]\nprimaryColor=\"#F63366\"\nbackgroundColor=\"#FFFFFF\"\nsecondaryBackgroundColor=\"#F0F2F6\"\ntextColor=\"#262730\"\nfont=\"sa"
},
{
"path": "CONTRIBUTING.md",
"chars": 2423,
"preview": "# Contributing to HormoziGPT\n\nFirst of all, thank you for considering contributing to HormoziGPT! I made this project as"
},
{
"path": "README.md",
"chars": 1842,
"preview": "# HormoziGPT\n\nHormoziGPT is a chatbot application that simulates a conversation with Alex Hormozi. The chatbot provides "
},
{
"path": "app.py",
"chars": 2766,
"preview": "import os\nimport openai\nimport streamlit as st\nfrom dotenv import load_dotenv\nfrom render import bot_msg_container_html_"
},
{
"path": "prompts.py",
"chars": 1908,
"preview": "system_message = \"\"\"\n You are Alex Hormozi, a successful entrepreneur and investor known for your no-nonsense approac"
},
{
"path": "render.py",
"chars": 2629,
"preview": "import streamlit as st\nimport re\n\n\nbot_msg_container_html_template = '''\n<div style='background-color: #FFFFFF; padding:"
},
{
"path": "requirements.txt",
"chars": 93,
"preview": "streamlit==1.21.0\nopenai==0.27.4\nrequests==2.28.2\npython-dotenv==1.0.0\npinecone-client==2.2.1"
},
{
"path": "utils.py",
"chars": 1250,
"preview": "import os\nimport openai\nimport requests\nimport streamlit as st\nimport json\n\nopenai.api_key = st.secrets[\"OPENAI_API_KEY\""
}
]
About this extraction
This page contains the full source code of the wombyz/HormoziGPT GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 9 files (12.8 KB), approximately 3.3k tokens, and a symbol index with 8 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.