Fixed dashboard

added brainmap
This commit is contained in:
Dani 2025-04-25 23:09:04 -04:00
parent e72678b242
commit 52cbba027e
10 changed files with 189 additions and 10 deletions

2
.gitignore vendored
View File

@ -174,3 +174,5 @@ cython_debug/
/data/memory/context.json
/data/memory/dreams.json
/data/memory/vocab.json
data/memory/vocab.json
data/memory/brainmap.json

View File

@ -1,9 +1,11 @@
from flask import Flask, render_template
from model.brainmap import get_brainmap
from model.journal import read_journal_entries
from model.memory import load_dreams
from model.tokenizer import Tokenizer
from model.abstraction import cluster_vocab
from context.context import load_context
import json
import os
import time
@ -43,6 +45,25 @@ def index():
next_cycle=remaining)
@app.route("/brainmap")
def brainmap():
map_data = get_brainmap()
nodes = []
links = []
for word, connections in map_data.items():
nodes.append({"id": word})
for linked_word, weight in connections.items():
links.append({
"source": word,
"target": linked_word,
"value": weight
})
return render_template("brainmap.html", nodes=json.dumps(nodes), links=json.dumps(links))
@app.route("/journal")
def journal():
entries = read_journal_entries()

View File

@ -0,0 +1,61 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Ruby's Brain Map</title>
<script src="https://cdn.jsdelivr.net/npm/force-graph"></script>
<style>
body {
background-color: #121212;
color: #e0e0e0;
margin: 0;
padding: 0;
overflow: hidden;
}
#graph {
width: 100vw;
height: 100vh;
}
.nav {
position: absolute;
top: 10px;
left: 10px;
background-color: #1e1e1e;
padding: 10px;
z-index: 1000;
}
.nav a {
color: #e0e0e0;
margin-right: 20px;
text-decoration: none;
}
</style>
</head>
<body>
<div class="nav">
<a href="/">🏠 Home</a>
<a href="/journal">📓 Journal</a>
<a href="/concepts">🧠 Concepts</a>
<a href="/brainmap">🕸️ Brain Map</a>
</div>
<div id="graph"></div>
<script>
const graphData = {
nodes: {{ nodes | safe }},
links: {{ links | safe }}
};
const Graph = ForceGraph()(document.getElementById('graph'))
.graphData(graphData)
.nodeAutoColorBy('id')
.nodeLabel('id')
.linkWidth(link => Math.log(link.value + 1))
.linkColor(() => 'rgba(255,255,255,0.2)')
.backgroundColor('#121212');
</script>
</body>
</html>

View File

@ -23,9 +23,31 @@
list-style-type: square;
padding-left: 20px;
}
.entry {
margin-bottom: 15px;
padding-bottom: 10px;
border-bottom: 1px solid #333;
}
.nav {
background-color: #1e1e1e;
padding: 10px;
margin-bottom: 20px;
}
.nav a {
color: #e0e0e0;
margin-right: 20px;
text-decoration: none;
}
</style>
</head>
<body>
<div class="nav">
<a href="/">🏠 Home</a>
<a href="/journal">📓 Journal</a>
<a href="/concepts">🧠 Concepts</a>
<a href="/brainmap">🕸️ Brain Map</a>
</div>
<h1>🧠 Ruby's Concept Clusters</h1>
{% for cluster_id, words in clusters.items() %}

View File

@ -30,6 +30,12 @@
</style>
</head>
<body>
<div style="background-color: #1e1e1e; padding: 10px; margin-bottom: 20px;">
<a href="/" style="color: #e0e0e0; margin-right: 20px;">🏠 Home</a>
<a href="/journal" style="color: #e0e0e0; margin-right: 20px;">📓 Journal</a>
<a href="/concepts" style="color: #e0e0e0; margin-right: 20px;">🧠 Concepts</a>
<a href="/brainmap" style="color: #e0e0e0;">🕸️ Brain Map</a>
</div>
<h1>Ruby is Running 🧠</h1>
<div class="section">

View File

@ -9,6 +9,7 @@
color: #e0e0e0;
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
padding: 20px;
margin: 0;
}
h1 {
color: #ffffff;
@ -18,13 +19,32 @@
padding-bottom: 10px;
border-bottom: 1px solid #333;
}
.nav {
background-color: #1e1e1e;
padding: 10px;
margin-bottom: 20px;
}
.nav a {
color: #e0e0e0;
margin-right: 20px;
text-decoration: none;
}
</style>
</head>
<body>
<div class="nav">
<a href="/">🏠 Home</a>
<a href="/journal">📓 Journal</a>
<a href="/concepts">🧠 Concepts</a>
<a href="/brainmap">🕸️ Brain Map</a>
</div>
<h1>📓 Ruby's Journal</h1>
{% for entry in entries %}
<div class="entry">{{ entry }}</div>
{% endfor %}
</body>
</html>

View File

@ -4,5 +4,11 @@
"how": 3,
"are": 4,
"you": 5,
"today": 6
"today": 6,
"the": 7,
"cat": 8,
"ran": 9,
"across": 10,
"sunny": 11,
"street": 12
}

View File

@ -9,11 +9,10 @@ def cluster_vocab(n_clusters=10):
vocab_items = list(tokenizer.vocab.items())
words, ids = zip(*vocab_items)
embeds = torch.nn.Embedding(len(ids), 256) # Same as model size
with torch.no_grad():
vectors = embeds(torch.tensor(list(ids)))
# Instead of embeddings, let's make random small vectors manually
vectors = torch.randn(len(ids), 64) # 64d random vectors for clustering
kmeans = KMeans(n_clusters=n_clusters)
kmeans = KMeans(n_clusters=min(n_clusters, len(ids)))
labels = kmeans.fit_predict(vectors.cpu().numpy())
clusters = {}

39
model/brainmap.py Normal file
View File

@ -0,0 +1,39 @@
import os
import json
from collections import defaultdict
BRAINMAP_FILE = "data/memory/brainmap.json"
def load_brainmap():
if os.path.exists(BRAINMAP_FILE):
with open(BRAINMAP_FILE, "r", encoding="utf-8") as f:
return json.load(f)
return {}
def save_brainmap(map_data):
with open(BRAINMAP_FILE, "w", encoding="utf-8") as f:
json.dump(map_data, f, indent=2)
brain_map = load_brainmap()
def update_brainmap(words):
for i, word in enumerate(words):
for j in range(i+1, len(words)):
w1 = word
w2 = words[j]
if w1 == w2:
continue
if w1 not in brain_map:
brain_map[w1] = {}
if w2 not in brain_map[w1]:
brain_map[w1][w2] = 0
brain_map[w1][w2] += 1
save_brainmap(brain_map)
def get_brainmap():
return brain_map

View File

@ -3,6 +3,7 @@ import time
from model.brain_state import model, tokenizer, DEVICE, optimizer, loss_fn
from context.context import add_to_context, get_recent_context
from model.dynamic_expand import expand_model_if_needed
from model.brainmap import update_brainmap
LOSS_FILE = "data/logs/loss.log"
@ -22,6 +23,8 @@ def train_on_message(text: str):
if len(tokens) < 2:
return
words = tokenizer.detokenize(tokens).split()
update_brainmap(words)
input_tensor = torch.tensor(tokens[:-1], dtype=torch.long, device=DEVICE).unsqueeze(0)
target_tensor = torch.tensor(tokens[1:], dtype=torch.long, device=DEVICE).unsqueeze(0)