Skip to content

Commit c4938a9

Browse files
committed
Add Friday Core LLM scaffold
1 parent 5d8ae24 commit c4938a9

5 files changed

Lines changed: 202 additions & 0 deletions

File tree

modules/friday-core/README.md

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
# Friday Core
2+
3+
This module is the starting point for building a Friday-style assistant stack for The Stark Project.
4+
5+
## LLM Direction
6+
7+
The LLM work lives under [src/llm](src/llm). The initial design focuses on a modular assistant architecture with:
8+
9+
- a model interface layer
10+
- a chat inference service
11+
- a tool-routing layer for plugins and actions
12+
- a future training pipeline for fine-tuning and adaptation
13+
14+
## Current Structure
15+
16+
- [src/llm/README.md](src/llm/README.md) — high-level architecture, roadmap, and technical decisions
17+
- [src/llm/core/model_interface.py](src/llm/core/model_interface.py) — base model and prompt wrapper abstractions
18+
- [src/llm/inference/chat_service.py](src/llm/inference/chat_service.py) — minimal chat orchestration layer
19+
- [src/llm/agents/tool_router.py](src/llm/agents/tool_router.py) — tool registration and dispatch
20+
21+
## Recommended Next Steps
22+
23+
1. Add a concrete backend implementation such as a Hugging Face model wrapper.
24+
2. Connect the assistant to the existing memory subsystem.
25+
3. Add a small plugin for a useful action like web lookup or command execution.
26+
4. Introduce a retrieval layer for long-term context.
27+
5. Build evaluation and safety checks for assistant behavior.
28+
29+
## Vision
30+
31+
The goal is to evolve this module into an assistant that feels like a Tony Stark-style companion: proactive, context-aware, connected to tools, and capable of acting across the Stark ecosystem.
Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
1+
# Friday Core LLM Workspace
2+
3+
This folder defines the initial architecture for building a custom assistant stack inspired by the Tony Stark / Friday concept: a fast, multimodal, context-aware assistant with tool use, memory, and safety boundaries.
4+
5+
## Goals
6+
7+
- Build a compact, trainable language model foundation for conversational assistance.
8+
- Add orchestration layers for memory, tools, and action execution.
9+
- Keep the design modular so it can evolve from local experiments to a production-grade assistant.
10+
11+
## Proposed Structure
12+
13+
- core/: shared tokenizer, config, model interfaces, and runtime utilities.
14+
- models/: model definitions, checkpoints, and architecture variants.
15+
- training/: data pipelines, tokenizer training, pretraining and fine-tuning scripts.
16+
- inference/: serving, batching, streaming, and prompt execution logic.
17+
- agents/: planner/executor patterns for tool-calling and multi-step reasoning.
18+
19+
## Recommended Infrastructure
20+
21+
### 1. Runtime
22+
- Python 3.11+
23+
- PyTorch or JAX for training and inference
24+
- Hugging Face Transformers for rapid prototyping
25+
- vLLM or TensorRT-LLM for optimized serving later
26+
27+
### 2. Data and Memory
28+
- Structured memory store for long-term facts
29+
- Episodic memory for recent conversations
30+
- Vector database for semantic retrieval
31+
- Event bus integration for tool and sensor subscriptions
32+
33+
### 3. Tooling and Services
34+
- Plugin interface for commands, APIs, and device control
35+
- Safety policy layer before action execution
36+
- Logging and observability for prompts, tool calls, and errors
37+
38+
### 4. Deployment
39+
- Local development first
40+
- Containerized inference service
41+
- Optional GPU-backed training environment
42+
- Edge deployment path for low-latency assistant use
43+
44+
## Phased Roadmap
45+
46+
### Phase 1: Foundations
47+
- Define the model interface and configuration schema
48+
- Build tokenizer and prompt templates
49+
- Create a minimal inference loop
50+
- Wire the assistant to the existing memory and plugin layers
51+
52+
### Phase 2: Capability Expansion
53+
- Add retrieval-augmented generation
54+
- Introduce tool calling and function routing
55+
- Support multimodal inputs such as voice and visual context
56+
- Add conversation state management
57+
58+
### Phase 3: Personality and Alignment
59+
- Fine-tune on domain-specific assistant behavior
60+
- Add safety policies and refusal handling
61+
- Improve memory selection and personalization
62+
- Optimize latency and response quality
63+
64+
### Phase 4: Stark-like Assistant Experience
65+
- High-speed voice interaction
66+
- Context-aware proactive suggestions
67+
- Multi-agent collaboration for planning and execution
68+
- Deep integration with robotics, dashboards, and hardware tools
69+
70+
## Technical Decisions
71+
72+
### Why a modular architecture?
73+
A modular design allows you to experiment with model variants without rewriting the assistant runtime.
74+
75+
### Why start with a small foundation model?
76+
A smaller model is easier to iterate on and is ideal for local development before scaling to larger architectures.
77+
78+
### Why separate training and inference?
79+
Training and inference have different dependencies, performance characteristics, and deployment constraints.
80+
81+
### Why integrate memory and tools early?
82+
An assistant feels intelligent when it can recall context and perform actions, not just generate text.
83+
84+
## Suggested First Implementation
85+
86+
1. Create a minimal model wrapper class.
87+
2. Add a prompt builder for system, user, and tool context.
88+
3. Connect the LLM to a simple in-memory conversation store.
89+
4. Add one tool plugin such as a weather lookup or command runner.
90+
5. Expose a basic chat endpoint.
91+
92+
## Notes
93+
94+
This is an initial blueprint. The long-term ambition is a Friday-like assistant that can reason, remember, act, and coordinate across the Stark ecosystem.
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
from typing import Callable, Dict, List
2+
3+
4+
class ToolRouter:
5+
"""Routes tool calls from LLM outputs to plugin handlers."""
6+
7+
def __init__(self) -> None:
8+
self.tools: Dict[str, Callable[..., str]] = {}
9+
10+
def register(self, name: str, handler: Callable[..., str]) -> None:
11+
self.tools[name] = handler
12+
13+
def route(self, tool_name: str, *args, **kwargs) -> str:
14+
if tool_name not in self.tools:
15+
raise KeyError(f"Tool '{tool_name}' is not registered")
16+
return self.tools[tool_name](*args, **kwargs)
17+
18+
def list_tools(self) -> List[str]:
19+
return sorted(self.tools.keys())
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
from dataclasses import dataclass
2+
from typing import Any, Dict, List, Optional
3+
4+
5+
@dataclass
6+
class ModelConfig:
7+
name: str = "friday-mini"
8+
max_context_length: int = 4096
9+
temperature: float = 0.7
10+
top_p: float = 0.95
11+
max_new_tokens: int = 512
12+
13+
14+
class LLMBackend:
15+
"""Abstract interface for any LLM backend used by Friday Core."""
16+
17+
def __init__(self, config: Optional[ModelConfig] = None) -> None:
18+
self.config = config or ModelConfig()
19+
20+
def generate(self, prompt: str, **kwargs: Any) -> str:
21+
raise NotImplementedError
22+
23+
def stream_generate(self, prompt: str, **kwargs: Any):
24+
raise NotImplementedError
25+
26+
27+
class FridayLLM:
28+
"""High-level wrapper that will connect the runtime to models, memory, and tools."""
29+
30+
def __init__(self, backend: LLMBackend) -> None:
31+
self.backend = backend
32+
33+
def chat(self, message: str, history: Optional[List[Dict[str, str]]] = None) -> str:
34+
prompt = self._build_prompt(message, history or [])
35+
return self.backend.generate(prompt)
36+
37+
def _build_prompt(self, message: str, history: List[Dict[str, str]]) -> str:
38+
conversation = "\n".join(
39+
f"{entry['role']}: {entry['content']}" for entry in history
40+
)
41+
return f"system: You are Friday, an assistant for The Stark Project.\n{conversation}\nuser: {message}\nassistant:"
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
from typing import List, Dict
2+
3+
from ..core.model_interface import FridayLLM, LLMBackend
4+
5+
6+
class ChatService:
7+
"""Minimal service wrapper for a Friday-style chat interface."""
8+
9+
def __init__(self, backend: LLMBackend) -> None:
10+
self.llm = FridayLLM(backend)
11+
self.history: List[Dict[str, str]] = []
12+
13+
def respond(self, message: str) -> str:
14+
response = self.llm.chat(message, self.history)
15+
self.history.append({"role": "user", "content": message})
16+
self.history.append({"role": "assistant", "content": response})
17+
return response

0 commit comments

Comments
 (0)