|
|
|
import os |
|
import re |
|
import glob |
|
import streamlit as st |
|
import streamlit.components.v1 as components |
|
from transformers import pipeline |
|
from urllib.parse import quote |
|
from datetime import datetime |
|
import pytz |
|
import base64 |
|
import pandas as pd |
|
import torch |
|
import torch.nn as nn |
|
import torch.optim as optim |
|
from torch.utils.data import DataLoader, TensorDataset |
|
|
|
st.set_page_config(page_title="AI Knowledge Tree Builder ππΏ", page_icon="π³β¨", layout="wide") |
|
|
|
trees = { |
|
"Biology": """ |
|
0. Biology Core Rules and Future Exceptions |
|
1. Central Dogma DNA RNA Protein |
|
- Current CRISPR RNA editing π§ͺ |
|
- Research Gene therapy siRNA π¬ |
|
- Future Programmable genetics π |
|
""", |
|
"AI Topics": """ |
|
1. Major AI Industry Players π |
|
1. Research Leaders π― |
|
- OpenAI: GPT-4 DALL-E Foundation Models π΅ |
|
""" |
|
} |
|
|
|
def parse_outline_to_mermaid(outline_text): |
|
lines = outline_text.strip().split('\n') |
|
nodes, edges, clicks, stack = [], [], [], [] |
|
for line in lines: |
|
indent = len(line) - len(line.lstrip()) |
|
level = indent // 4 |
|
label = re.sub(r'^[#*\->\d\.\s]+', '', line.strip()) |
|
if label: |
|
node_id = f"N{len(nodes)}" |
|
nodes.append(f'{node_id}["{label}"]') |
|
clicks.append(f'click {node_id} "?q={quote(label)}" _blank') |
|
if stack: |
|
parent_level = stack[-1][0] |
|
if level > parent_level: |
|
edges.append(f"{stack[-1][1]} --> {node_id}") |
|
stack.append((level, node_id)) |
|
else: |
|
while stack and stack[-1][0] >= level: |
|
stack.pop() |
|
if stack: |
|
edges.append(f"{stack[-1][1]} --> {node_id}") |
|
stack.append((level, node_id)) |
|
else: |
|
stack.append((level, node_id)) |
|
return "%%{init: {'themeVariables': {'fontSize': '18px'}}}%%\nflowchart LR\n" + "\n".join(nodes + edges + clicks) |
|
|
|
def generate_mermaid_html(mermaid_code): |
|
return f""" |
|
<html><head><script src="https://cdn.jsdelivr.net/npm/mermaid/dist/mermaid.min.js"></script> |
|
<style>.centered-mermaid{{display:flex;justify-content:center;margin:20px auto;}}</style></head> |
|
<body><div class="mermaid centered-mermaid">{mermaid_code}</div> |
|
<script>mermaid.initialize({{startOnLoad:true}});</script></body></html> |
|
""" |
|
|
|
def grow_tree(base_tree, new_node_name, parent_node): |
|
lines = base_tree.strip().split('\n') |
|
new_lines = [] |
|
added = False |
|
for line in lines: |
|
new_lines.append(line) |
|
if parent_node in line and not added: |
|
indent = len(line) - len(line.lstrip()) |
|
new_lines.append(f"{' ' * (indent + 4)}- {new_node_name} π±") |
|
added = True |
|
return "\n".join(new_lines) |
|
|
|
def get_download_link(file_path, mime_type="text/plain"): |
|
with open(file_path, 'rb') as f: |
|
data = f.read() |
|
b64 = base64.b64encode(data).decode() |
|
return f'<a href="data:{mime_type};base64,{b64}" download="{file_path}">Download {file_path}</a>' |
|
|
|
@st.cache_resource |
|
def load_generator(): |
|
return pipeline("text-generation", model="distilgpt2") |
|
|
|
|
|
st.title("π³ AI Knowledge Tree Builder π±") |
|
|
|
if 'current_tree' not in st.session_state: |
|
if os.path.exists("current_tree.md"): |
|
with open("current_tree.md", "r") as f: |
|
st.session_state['current_tree'] = f.read() |
|
else: |
|
st.session_state['current_tree'] = trees["Biology"] |
|
|
|
selected_tree = st.selectbox("Select Knowledge Tree", list(trees.keys())) |
|
if selected_tree != st.session_state.get('selected_tree_name', 'Biology'): |
|
st.session_state['current_tree'] = trees[selected_tree] |
|
st.session_state['selected_tree_name'] = selected_tree |
|
with open("current_tree.md", "w") as f: |
|
f.write(st.session_state['current_tree']) |
|
|
|
new_node = st.text_input("Add New Node") |
|
parent_node = st.text_input("Parent Node") |
|
if st.button("Grow Tree π±") and new_node and parent_node: |
|
st.session_state['current_tree'] = grow_tree(st.session_state['current_tree'], new_node, parent_node) |
|
with open("current_tree.md", "w") as f: |
|
f.write(st.session_state['current_tree']) |
|
st.success(f"Added '{new_node}' under '{parent_node}'!") |
|
|
|
st.markdown("### Knowledge Tree Visualization") |
|
mermaid_code = parse_outline_to_mermaid(st.session_state['current_tree']) |
|
components.html(generate_mermaid_html(mermaid_code), height=600) |
|
|
|
if st.button("Export Tree as Markdown"): |
|
export_md = f"# Knowledge Tree\n\n## Outline\n{st.session_state['current_tree']}\n\n## Mermaid Diagram\n```mermaid\n{mermaid_code}\n```" |
|
with open("knowledge_tree.md", "w") as f: |
|
f.write(export_md) |
|
st.markdown(get_download_link("knowledge_tree.md", "text/markdown"), unsafe_allow_html=True) |
|
|
|
st.subheader("Build ML Model from CSV") |
|
uploaded_file = st.file_uploader("Upload CSV", type="csv") |
|
if uploaded_file: |
|
df = pd.read_csv(uploaded_file) |
|
st.write("Columns:", df.columns.tolist()) |
|
feature_cols = st.multiselect("Select feature columns", df.columns) |
|
target_col = st.selectbox("Select target column", df.columns) |
|
if st.button("Train Model"): |
|
X = df[feature_cols].values |
|
y = df[target_col].values |
|
X_tensor = torch.tensor(X, dtype=torch.float32) |
|
y_tensor = torch.tensor(y, dtype=torch.float32).view(-1, 1) |
|
dataset = TensorDataset(X_tensor, y_tensor) |
|
loader = DataLoader(dataset, batch_size=32, shuffle=True) |
|
model = nn.Linear(X.shape[1], 1) |
|
criterion = nn.MSELoss() |
|
optimizer = optim.Adam(model.parameters(), lr=0.01) |
|
for epoch in range(10): |
|
for batch_X, batch_y in loader: |
|
optimizer.zero_grad() |
|
outputs = model(batch_X) |
|
loss = criterion(outputs, batch_y) |
|
loss.backward() |
|
optimizer.step() |
|
torch.save(model.state_dict(), "model.pth") |
|
app_code = f""" |
|
import streamlit as st |
|
import torch |
|
import torch.nn as nn |
|
|
|
model = nn.Linear({len(feature_cols)}, 1) |
|
model.load_state_dict(torch.load("model.pth")) |
|
model.eval() |
|
|
|
st.title("ML Model Demo") |
|
inputs = [] |
|
for col in {feature_cols}: |
|
inputs.append(st.number_input(col)) |
|
if st.button("Predict"): |
|
input_tensor = torch.tensor([inputs], dtype=torch.float32) |
|
prediction = model(input_tensor).item() |
|
st.write(f"Predicted {target_col}: {{prediction}}") |
|
""" |
|
with open("app.py", "w") as f: |
|
f.write(app_code) |
|
reqs = "streamlit\ntorch\npandas\n" |
|
with open("requirements.txt", "w") as f: |
|
f.write(reqs) |
|
readme = """ |
|
# ML Model Demo |
|
|
|
## How to run |
|
1. Install requirements: `pip install -r requirements.txt` |
|
2. Run the app: `streamlit run app.py` |
|
3. Input feature values and click "Predict". |
|
""" |
|
with open("README.md", "w") as f: |
|
f.write(readme) |
|
st.markdown(get_download_link("model.pth", "application/octet-stream"), unsafe_allow_html=True) |
|
st.markdown(get_download_link("app.py", "text/plain"), unsafe_allow_html=True) |
|
st.markdown(get_download_link("requirements.txt", "text/plain"), unsafe_allow_html=True) |
|
st.markdown(get_download_link("README.md", "text/markdown"), unsafe_allow_html=True) |