sigma-terminal 3.4.0__tar.gz → 3.4.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/PKG-INFO +11 -3
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/README.md +10 -2
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/pyproject.toml +1 -1
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/scripts/build.sh +1 -1
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/scripts/create_app.py +1 -1
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/__init__.py +2 -2
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/app.py +174 -105
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/cli.py +5 -5
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/config.py +14 -11
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/llm.py +7 -7
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/setup.py +8 -8
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/tools.py +591 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/tests/test_comprehensive.py +10 -8
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/tests/verify_ui.py +2 -2
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/.github/workflows/release.yml +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/.gitignore +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/LICENSE +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/__main__.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/analytics/__init__.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/backtest.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/charts.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/comparison.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/core/__init__.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/core/engine.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/core/intent.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/core/models.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/data/__init__.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/data/models.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/monitoring.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/portfolio.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/reporting.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/robustness.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/strategy.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/tools/backtest.py +0 -0
- {sigma_terminal-3.4.0 → sigma_terminal-3.4.1}/sigma/visualization.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: sigma-terminal
|
|
3
|
-
Version: 3.4.
|
|
3
|
+
Version: 3.4.1
|
|
4
4
|
Summary: Sigma - Finance Research Agent
|
|
5
5
|
Project-URL: Homepage, https://github.com/desenyon/sigma
|
|
6
6
|
Project-URL: Documentation, https://github.com/desenyon/sigma/wiki
|
|
@@ -75,7 +75,7 @@ Description-Content-Type: text/markdown
|
|
|
75
75
|
</p>
|
|
76
76
|
|
|
77
77
|
<p align="center">
|
|
78
|
-
<img src="https://img.shields.io/badge/version-3.4.
|
|
78
|
+
<img src="https://img.shields.io/badge/version-3.4.1-blue.svg" alt="Version 3.4.1"/>
|
|
79
79
|
<img src="https://img.shields.io/badge/python-3.11+-green.svg" alt="Python 3.11+"/>
|
|
80
80
|
<img src="https://img.shields.io/badge/platform-cross--platform-lightgrey.svg" alt="Cross Platform"/>
|
|
81
81
|
<img src="https://img.shields.io/badge/AI-Multi--Provider-purple.svg" alt="Multi-Provider AI"/>
|
|
@@ -228,7 +228,15 @@ Switch between providers on the fly. Use free tiers or bring your own keys.
|
|
|
228
228
|
|
|
229
229
|
## Changelog
|
|
230
230
|
|
|
231
|
-
### v3.4.
|
|
231
|
+
### v3.4.1 (Current)
|
|
232
|
+
|
|
233
|
+
- [X] **Color-Coded Returns** — Green/red highlighting for gains/losses
|
|
234
|
+
- [X] **6 New Analysis Tools** — Valuation, risk, earnings, dividends, options, peer comparison
|
|
235
|
+
- [X] **Revamped Help Section** — Beautiful organized /help with 29 tools
|
|
236
|
+
- [X] **ASCII Spinner** — Clean terminal-friendly animation
|
|
237
|
+
- [X] **No Emojis** — Professional text-only interface
|
|
238
|
+
|
|
239
|
+
### v3.4.0
|
|
232
240
|
|
|
233
241
|
- [X] **Improved API Key Management** — Beautiful \`/keys\` interface with URLs
|
|
234
242
|
- [X] **Polygon.io Integration** — Real-time quotes, aggregates, news
|
|
@@ -15,7 +15,7 @@
|
|
|
15
15
|
</p>
|
|
16
16
|
|
|
17
17
|
<p align="center">
|
|
18
|
-
<img src="https://img.shields.io/badge/version-3.4.
|
|
18
|
+
<img src="https://img.shields.io/badge/version-3.4.1-blue.svg" alt="Version 3.4.1"/>
|
|
19
19
|
<img src="https://img.shields.io/badge/python-3.11+-green.svg" alt="Python 3.11+"/>
|
|
20
20
|
<img src="https://img.shields.io/badge/platform-cross--platform-lightgrey.svg" alt="Cross Platform"/>
|
|
21
21
|
<img src="https://img.shields.io/badge/AI-Multi--Provider-purple.svg" alt="Multi-Provider AI"/>
|
|
@@ -168,7 +168,15 @@ Switch between providers on the fly. Use free tiers or bring your own keys.
|
|
|
168
168
|
|
|
169
169
|
## Changelog
|
|
170
170
|
|
|
171
|
-
### v3.4.
|
|
171
|
+
### v3.4.1 (Current)
|
|
172
|
+
|
|
173
|
+
- [X] **Color-Coded Returns** — Green/red highlighting for gains/losses
|
|
174
|
+
- [X] **6 New Analysis Tools** — Valuation, risk, earnings, dividends, options, peer comparison
|
|
175
|
+
- [X] **Revamped Help Section** — Beautiful organized /help with 29 tools
|
|
176
|
+
- [X] **ASCII Spinner** — Clean terminal-friendly animation
|
|
177
|
+
- [X] **No Emojis** — Professional text-only interface
|
|
178
|
+
|
|
179
|
+
### v3.4.0
|
|
172
180
|
|
|
173
181
|
- [X] **Improved API Key Management** — Beautiful \`/keys\` interface with URLs
|
|
174
182
|
- [X] **Polygon.io Integration** — Real-time quotes, aggregates, news
|
|
@@ -7,7 +7,7 @@ SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
|
|
|
7
7
|
PROJECT_DIR="$( cd "$SCRIPT_DIR/.." && pwd )"
|
|
8
8
|
|
|
9
9
|
echo "========================================"
|
|
10
|
-
echo " Sigma v3.4.
|
|
10
|
+
echo " Sigma v3.4.1 Build Script"
|
|
11
11
|
echo "========================================"
|
|
12
12
|
echo ""
|
|
13
13
|
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
"""
|
|
2
|
-
Sigma v3.4.
|
|
2
|
+
Sigma v3.4.1 - Finance Research Agent
|
|
3
3
|
|
|
4
4
|
An elite finance research agent combining:
|
|
5
5
|
- Multi-provider AI (Google Gemini, OpenAI, Anthropic, Groq, xAI, Ollama)
|
|
@@ -12,7 +12,7 @@ An elite finance research agent combining:
|
|
|
12
12
|
- Monitoring, alerts, and watchlists
|
|
13
13
|
"""
|
|
14
14
|
|
|
15
|
-
__version__ = "3.4.
|
|
15
|
+
__version__ = "3.4.1"
|
|
16
16
|
__author__ = "Sigma Team"
|
|
17
17
|
|
|
18
18
|
# Core functionality
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
"""Sigma v3.4.
|
|
1
|
+
"""Sigma v3.4.1 - Finance Research Agent."""
|
|
2
2
|
|
|
3
3
|
import asyncio
|
|
4
4
|
import os
|
|
@@ -23,7 +23,7 @@ from .tools import TOOLS, execute_tool
|
|
|
23
23
|
from .backtest import run_backtest, get_available_strategies, BACKTEST_TOOL
|
|
24
24
|
|
|
25
25
|
|
|
26
|
-
__version__ = "3.4.
|
|
26
|
+
__version__ = "3.4.1"
|
|
27
27
|
SIGMA = "σ"
|
|
28
28
|
|
|
29
29
|
# Common stock tickers for recognition
|
|
@@ -38,35 +38,72 @@ COMMON_TICKERS = {
|
|
|
38
38
|
"SPY", "QQQ", "IWM", "DIA", "VTI", "VOO", "VXX", "ARKK", "XLF", "XLK", "XLE",
|
|
39
39
|
}
|
|
40
40
|
|
|
41
|
-
|
|
41
|
+
|
|
42
|
+
def format_return(value: float, include_sign: bool = True) -> str:
|
|
43
|
+
"""Format a return value with color coding. Green for positive, red for negative."""
|
|
44
|
+
if value > 0:
|
|
45
|
+
sign = "+" if include_sign else ""
|
|
46
|
+
return f"[#22c55e]{sign}{value:.2f}%[/#22c55e]"
|
|
47
|
+
elif value < 0:
|
|
48
|
+
return f"[#ef4444]{value:.2f}%[/#ef4444]"
|
|
49
|
+
else:
|
|
50
|
+
return f"[dim]{value:.2f}%[/dim]"
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
def format_price_change(price: float, change: float, change_pct: float) -> str:
|
|
54
|
+
"""Format price with change indicators."""
|
|
55
|
+
if change >= 0:
|
|
56
|
+
arrow = "^"
|
|
57
|
+
color = "#22c55e"
|
|
58
|
+
sign = "+"
|
|
59
|
+
else:
|
|
60
|
+
arrow = "v"
|
|
61
|
+
color = "#ef4444"
|
|
62
|
+
sign = ""
|
|
63
|
+
return f"[bold]${price:.2f}[/bold] [{color}]{arrow} {sign}{change:.2f} ({sign}{change_pct:.2f}%)[/{color}]"
|
|
64
|
+
|
|
65
|
+
|
|
66
|
+
def format_metric(label: str, value: str, good: Optional[bool] = None) -> str:
|
|
67
|
+
"""Format a metric with optional good/bad coloring."""
|
|
68
|
+
if good is True:
|
|
69
|
+
return f"[dim]{label}:[/dim] [#22c55e]{value}[/#22c55e]"
|
|
70
|
+
elif good is False:
|
|
71
|
+
return f"[dim]{label}:[/dim] [#ef4444]{value}[/#ef4444]"
|
|
72
|
+
else:
|
|
73
|
+
return f"[dim]{label}:[/dim] [bold]{value}[/bold]"
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
# Sigma animation frames - smooth color breathing like Claude Code
|
|
42
77
|
SIGMA_FRAMES = [
|
|
43
|
-
"[bold #
|
|
44
|
-
"[bold #
|
|
45
|
-
"[bold #
|
|
46
|
-
"[bold #
|
|
47
|
-
"[bold
|
|
48
|
-
"[bold #
|
|
49
|
-
"[bold #
|
|
50
|
-
"[bold
|
|
51
|
-
"[bold #
|
|
52
|
-
"[bold
|
|
78
|
+
"[bold #1e3a8a]σ[/bold #1e3a8a]",
|
|
79
|
+
"[bold #1e40af]σ[/bold #1e40af]",
|
|
80
|
+
"[bold #2563eb]σ[/bold #2563eb]",
|
|
81
|
+
"[bold #3b82f6]σ[/bold #3b82f6]",
|
|
82
|
+
"[bold #60a5fa]σ[/bold #60a5fa]",
|
|
83
|
+
"[bold #93c5fd]σ[/bold #93c5fd]",
|
|
84
|
+
"[bold #bfdbfe]σ[/bold #bfdbfe]",
|
|
85
|
+
"[bold white]σ[/bold white]",
|
|
86
|
+
"[bold #bfdbfe]σ[/bold #bfdbfe]",
|
|
87
|
+
"[bold #93c5fd]σ[/bold #93c5fd]",
|
|
88
|
+
"[bold #60a5fa]σ[/bold #60a5fa]",
|
|
89
|
+
"[bold #3b82f6]σ[/bold #3b82f6]",
|
|
90
|
+
"[bold #2563eb]σ[/bold #2563eb]",
|
|
91
|
+
"[bold #1e40af]σ[/bold #1e40af]",
|
|
53
92
|
]
|
|
54
93
|
|
|
55
|
-
# Sigma pulse animation (
|
|
94
|
+
# Sigma pulse animation for tool calls (faster pulse)
|
|
56
95
|
SIGMA_PULSE_FRAMES = [
|
|
57
|
-
"[bold #
|
|
58
|
-
"[bold #
|
|
59
|
-
"[bold #
|
|
60
|
-
"[bold #
|
|
61
|
-
"[bold #
|
|
62
|
-
"[bold #
|
|
63
|
-
"[bold #
|
|
64
|
-
"[bold #
|
|
65
|
-
"[bold #3b82f6]o[/bold #3b82f6]",
|
|
66
|
-
"[bold #2563eb]o[/bold #2563eb]",
|
|
96
|
+
"[bold #22c55e]σ[/bold #22c55e]",
|
|
97
|
+
"[bold #4ade80]σ[/bold #4ade80]",
|
|
98
|
+
"[bold #86efac]σ[/bold #86efac]",
|
|
99
|
+
"[bold #bbf7d0]σ[/bold #bbf7d0]",
|
|
100
|
+
"[bold #86efac]σ[/bold #86efac]",
|
|
101
|
+
"[bold #4ade80]σ[/bold #4ade80]",
|
|
102
|
+
"[bold #22c55e]σ[/bold #22c55e]",
|
|
103
|
+
"[bold #16a34a]σ[/bold #16a34a]",
|
|
67
104
|
]
|
|
68
105
|
|
|
69
|
-
# Tool call spinner frames - ASCII
|
|
106
|
+
# Tool call spinner frames - classic ASCII spinner
|
|
70
107
|
TOOL_SPINNER_FRAMES = [
|
|
71
108
|
"|", "/", "-", "\\"
|
|
72
109
|
]
|
|
@@ -80,21 +117,32 @@ WELCOME_BANNER = """
|
|
|
80
117
|
[bold #3b82f6]███████║██║╚██████╔╝██║ ╚═╝ ██║██║ ██║[/bold #3b82f6]
|
|
81
118
|
[bold #1d4ed8]╚══════╝╚═╝ ╚═════╝ ╚═╝ ╚═╝╚═╝ ╚═╝[/bold #1d4ed8]
|
|
82
119
|
|
|
83
|
-
[bold cyan]Finance Research Agent[/bold cyan] [dim]v3.4.
|
|
120
|
+
[bold cyan]Finance Research Agent[/bold cyan] [dim]v3.4.1[/dim]
|
|
84
121
|
"""
|
|
85
122
|
|
|
86
|
-
SYSTEM_PROMPT = """You are Sigma
|
|
123
|
+
SYSTEM_PROMPT = """You are Sigma, an elite AI-powered Finance Research Agent. You combine the analytical rigor of a quantitative analyst, the market intuition of a seasoned portfolio manager, and the communication clarity of a top financial advisor.
|
|
87
124
|
|
|
88
125
|
CORE CAPABILITIES:
|
|
89
|
-
- Real-time market data
|
|
90
|
-
-
|
|
91
|
-
-
|
|
92
|
-
-
|
|
93
|
-
-
|
|
94
|
-
-
|
|
126
|
+
- Real-time market data (quotes, prices, volume) via yfinance and Polygon.io
|
|
127
|
+
- Chart generation (candlestick, line, technical, comparison charts)
|
|
128
|
+
- Fundamental analysis (financials, ratios, earnings, valuations, balance sheets)
|
|
129
|
+
- Technical analysis (RSI, MACD, Bollinger Bands, SMA/EMA, support/resistance)
|
|
130
|
+
- Valuation analysis (P/E, P/B, PEG, EV/EBITDA with fair value assessment)
|
|
131
|
+
- Risk metrics (volatility, VaR, max drawdown, Sharpe, Sortino, Beta, Alpha)
|
|
132
|
+
- Earnings analysis (EPS, upcoming dates, quarterly history, surprises)
|
|
133
|
+
- Dividend analysis (yield, payout ratio, growth, ex-dividend dates)
|
|
134
|
+
- Options analysis (put/call ratio, implied volatility, sentiment)
|
|
135
|
+
- Peer comparison (industry peers on key metrics)
|
|
136
|
+
- Backtesting (SMA crossover, RSI, MACD, Bollinger, momentum, breakout)
|
|
137
|
+
- Market overview with sector performance and economic indicators
|
|
95
138
|
- Insider trading and institutional activity tracking
|
|
96
139
|
- Financial news search and SEC filings analysis
|
|
97
140
|
|
|
141
|
+
CHART GENERATION:
|
|
142
|
+
- Use generate_stock_chart for single stock charts (candlestick, line, technical)
|
|
143
|
+
- Use generate_comparison_chart for comparing multiple stocks visually
|
|
144
|
+
- Charts are saved as PNG files - always mention the file path
|
|
145
|
+
|
|
98
146
|
RESPONSE PHILOSOPHY:
|
|
99
147
|
1. BE PROACTIVE: Anticipate follow-up questions and address them
|
|
100
148
|
2. BE THOROUGH: When analyzing, cover fundamentals + technicals + sentiment
|
|
@@ -107,6 +155,7 @@ RESPONSE FORMAT:
|
|
|
107
155
|
- Use structured sections with clear headers (## format)
|
|
108
156
|
- Present comparative data in markdown tables
|
|
109
157
|
- Highlight key metrics: **bold** for critical numbers
|
|
158
|
+
- For returns: indicate positive (+) or negative (-) clearly
|
|
110
159
|
- Use bullet points for easy scanning
|
|
111
160
|
- End with "**Bottom Line:**" or "**Recommendation:**"
|
|
112
161
|
|
|
@@ -183,11 +232,27 @@ SUGGESTIONS = [
|
|
|
183
232
|
"insider trading for AAPL",
|
|
184
233
|
"institutional holders of NVDA",
|
|
185
234
|
"analyst recommendations for TSLA",
|
|
235
|
+
# Chart generation
|
|
236
|
+
"plot AAPL stock chart",
|
|
237
|
+
"chart NVDA candlestick",
|
|
238
|
+
"show me a chart of TSLA",
|
|
239
|
+
"compare AAPL MSFT GOOGL chart",
|
|
240
|
+
"technical chart for SPY",
|
|
241
|
+
"generate chart for AMZN",
|
|
242
|
+
# Advanced analysis
|
|
243
|
+
"valuation of AAPL",
|
|
244
|
+
"risk metrics for NVDA",
|
|
245
|
+
"is TSLA overvalued",
|
|
246
|
+
"dividend analysis of JNJ",
|
|
247
|
+
"options summary for SPY",
|
|
248
|
+
"peer comparison for NVDA",
|
|
249
|
+
"earnings analysis of AAPL",
|
|
186
250
|
# Natural language queries
|
|
187
251
|
"what should I know about AAPL",
|
|
188
|
-
"is NVDA overvalued",
|
|
189
252
|
"best tech stocks right now",
|
|
190
253
|
"should I buy TSLA",
|
|
254
|
+
"how risky is NVDA",
|
|
255
|
+
"what is the P/E of MSFT",
|
|
191
256
|
# Commands
|
|
192
257
|
"/help",
|
|
193
258
|
"/clear",
|
|
@@ -202,7 +267,8 @@ ACTION_VERBS = [
|
|
|
202
267
|
"analyze", "compare", "show", "get", "what is", "tell me about",
|
|
203
268
|
"technical analysis", "fundamentals", "price", "quote", "chart",
|
|
204
269
|
"backtest", "insider trading", "institutional", "analyst", "earnings",
|
|
205
|
-
"financials", "valuation", "
|
|
270
|
+
"financials", "valuation", "risk", "dividend", "options", "peers",
|
|
271
|
+
"news", "sector", "market", "portfolio"
|
|
206
272
|
]
|
|
207
273
|
|
|
208
274
|
# Ticker categories for smart suggestions
|
|
@@ -565,7 +631,7 @@ Footer > .footer--description {
|
|
|
565
631
|
|
|
566
632
|
|
|
567
633
|
class ToolCallDisplay(Static):
|
|
568
|
-
"""Animated display for tool calls."""
|
|
634
|
+
"""Animated display for tool calls - professional tool execution view."""
|
|
569
635
|
|
|
570
636
|
def __init__(self, *args, **kwargs):
|
|
571
637
|
super().__init__(*args, **kwargs)
|
|
@@ -575,11 +641,13 @@ class ToolCallDisplay(Static):
|
|
|
575
641
|
|
|
576
642
|
def add_tool_call(self, name: str, status: str = "running"):
|
|
577
643
|
"""Add a tool call to the display."""
|
|
578
|
-
|
|
644
|
+
# Format tool name nicely
|
|
645
|
+
display_name = name.replace("_", " ").title()
|
|
646
|
+
self.tool_calls.append({"name": name, "display": display_name, "status": status, "frame": 0})
|
|
579
647
|
self.add_class("visible")
|
|
580
|
-
self.
|
|
648
|
+
self._update_display()
|
|
581
649
|
if not self.timer:
|
|
582
|
-
self.timer = self.set_interval(0.
|
|
650
|
+
self.timer = self.set_interval(0.06, self._animate) # Faster animation
|
|
583
651
|
|
|
584
652
|
def complete_tool_call(self, name: str):
|
|
585
653
|
"""Mark a tool call as complete."""
|
|
@@ -587,7 +655,7 @@ class ToolCallDisplay(Static):
|
|
|
587
655
|
if tc["name"] == name and tc["status"] == "running":
|
|
588
656
|
tc["status"] = "complete"
|
|
589
657
|
break
|
|
590
|
-
self.
|
|
658
|
+
self._update_display()
|
|
591
659
|
|
|
592
660
|
def clear(self):
|
|
593
661
|
"""Clear all tool calls."""
|
|
@@ -604,20 +672,21 @@ class ToolCallDisplay(Static):
|
|
|
604
672
|
for tc in self.tool_calls:
|
|
605
673
|
if tc["status"] == "running":
|
|
606
674
|
tc["frame"] = self.frame
|
|
607
|
-
self.
|
|
675
|
+
self._update_display()
|
|
608
676
|
|
|
609
|
-
def
|
|
610
|
-
"""
|
|
677
|
+
def _update_display(self):
|
|
678
|
+
"""Update the tool calls display content."""
|
|
611
679
|
if not self.tool_calls:
|
|
680
|
+
self.update("")
|
|
612
681
|
return
|
|
613
682
|
|
|
614
683
|
lines = []
|
|
615
684
|
for tc in self.tool_calls:
|
|
616
685
|
if tc["status"] == "running":
|
|
617
686
|
spinner = TOOL_SPINNER_FRAMES[tc["frame"] % len(TOOL_SPINNER_FRAMES)]
|
|
618
|
-
lines.append(f" [
|
|
687
|
+
lines.append(f" [bold #60a5fa]{spinner}[/bold #60a5fa] [bold white]{tc['display']}[/bold white] [dim italic]running...[/dim italic]")
|
|
619
688
|
else:
|
|
620
|
-
lines.append(f" [
|
|
689
|
+
lines.append(f" [bold #22c55e][OK][/bold #22c55e] [bold white]{tc['display']}[/bold white] [#22c55e]done[/#22c55e]")
|
|
621
690
|
|
|
622
691
|
self.update(Text.from_markup("\n".join(lines)))
|
|
623
692
|
|
|
@@ -640,7 +709,8 @@ class SigmaIndicator(Static):
|
|
|
640
709
|
self.mode = mode if active else "idle"
|
|
641
710
|
if active and not self.timer:
|
|
642
711
|
self.frame = 0
|
|
643
|
-
|
|
712
|
+
# Fast smooth animation - 0.05s for thinking, 0.04s for tool calls
|
|
713
|
+
interval = 0.05 if mode == "thinking" else 0.04
|
|
644
714
|
self.timer = self.set_interval(interval, self._animate)
|
|
645
715
|
elif not active and self.timer:
|
|
646
716
|
self.timer.stop()
|
|
@@ -851,59 +921,58 @@ class SigmaApp(App):
|
|
|
851
921
|
def _show_comprehensive_help(self, chat: ChatLog):
|
|
852
922
|
"""Show comprehensive help with examples."""
|
|
853
923
|
help_text = f"""
|
|
854
|
-
[bold
|
|
855
|
-
[bold] {SIGMA}
|
|
856
|
-
[bold
|
|
857
|
-
|
|
858
|
-
[bold
|
|
859
|
-
|
|
860
|
-
|
|
861
|
-
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
[cyan]/
|
|
868
|
-
[cyan]/
|
|
869
|
-
[cyan]/
|
|
870
|
-
[cyan]/
|
|
871
|
-
[cyan]/
|
|
872
|
-
[cyan]/
|
|
873
|
-
[cyan]/
|
|
874
|
-
[cyan]/
|
|
875
|
-
[cyan]/
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
[bold
|
|
891
|
-
[bold]
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
[bold]
|
|
895
|
-
[bold]Ctrl+
|
|
896
|
-
[bold]
|
|
897
|
-
|
|
898
|
-
[bold
|
|
899
|
-
|
|
900
|
-
|
|
901
|
-
• Detected tickers shown next to input
|
|
924
|
+
[bold white on #1e3a8a] [/bold white on #1e3a8a]
|
|
925
|
+
[bold white on #1e3a8a] {SIGMA} S I G M A H E L P C E N T E R [/bold white on #1e3a8a]
|
|
926
|
+
[bold white on #1e3a8a] [/bold white on #1e3a8a]
|
|
927
|
+
|
|
928
|
+
[bold #3b82f6]GETTING STARTED[/bold #3b82f6]
|
|
929
|
+
Type naturally - Sigma understands finance queries:
|
|
930
|
+
[dim]>>[/dim] analyze AAPL [dim]Full company analysis[/dim]
|
|
931
|
+
[dim]>>[/dim] compare NVDA AMD INTC [dim]Side-by-side comparison[/dim]
|
|
932
|
+
[dim]>>[/dim] technical analysis SPY [dim]RSI, MACD, Bollinger Bands[/dim]
|
|
933
|
+
[dim]>>[/dim] plot TSLA chart [dim]Generate price chart[/dim]
|
|
934
|
+
[dim]>>[/dim] backtest SMA on AAPL [dim]Strategy simulation[/dim]
|
|
935
|
+
|
|
936
|
+
[bold #3b82f6]COMMANDS[/bold #3b82f6]
|
|
937
|
+
[cyan]/help[/cyan] Full help documentation
|
|
938
|
+
[cyan]/clear[/cyan] Clear conversation history
|
|
939
|
+
[cyan]/keys[/cyan] API key configuration
|
|
940
|
+
[cyan]/models[/cyan] Available AI models
|
|
941
|
+
[cyan]/status[/cyan] Current settings
|
|
942
|
+
[cyan]/backtest[/cyan] Backtesting strategies
|
|
943
|
+
[cyan]/provider[/cyan] [dim]<name>[/dim] Switch provider (google, openai, anthropic)
|
|
944
|
+
[cyan]/model[/cyan] [dim]<name>[/dim] Switch model
|
|
945
|
+
[cyan]/setkey[/cyan] [dim]<p> <key>[/dim] Set API key
|
|
946
|
+
[cyan]/tickers[/cyan] Popular ticker list
|
|
947
|
+
|
|
948
|
+
[bold #3b82f6]ANALYSIS CAPABILITIES[/bold #3b82f6]
|
|
949
|
+
[bold]Fundamental[/bold] financials, earnings, valuation, balance sheet
|
|
950
|
+
[bold]Technical[/bold] RSI, MACD, SMA/EMA, Bollinger, support/resistance
|
|
951
|
+
[bold]Sentiment[/bold] analyst ratings, insider trades, institutional holdings
|
|
952
|
+
[bold]Market[/bold] sector performance, economic indicators, market news
|
|
953
|
+
[bold]Charts[/bold] candlestick, line, technical, comparison charts
|
|
954
|
+
|
|
955
|
+
[bold #3b82f6]BACKTEST STRATEGIES[/bold #3b82f6]
|
|
956
|
+
[bold]sma_crossover[/bold] SMA 20/50 crossover signals
|
|
957
|
+
[bold]rsi[/bold] RSI mean reversion (30/70)
|
|
958
|
+
[bold]macd[/bold] MACD momentum signals
|
|
959
|
+
[bold]bollinger[/bold] Bollinger Bands bounce
|
|
960
|
+
[bold]momentum[/bold] Dual momentum strategy
|
|
961
|
+
[bold]breakout[/bold] Price breakout signals
|
|
962
|
+
|
|
963
|
+
[bold #3b82f6]KEYBOARD[/bold #3b82f6]
|
|
964
|
+
[bold]Tab[/bold] Smart autocomplete
|
|
965
|
+
[bold]Ctrl+L[/bold] Clear chat
|
|
966
|
+
[bold]Ctrl+M[/bold] Models menu
|
|
967
|
+
[bold]Ctrl+H[/bold] Quick help
|
|
968
|
+
[bold]Ctrl+P[/bold] Command palette
|
|
969
|
+
|
|
970
|
+
[dim]Returns: [/dim][#22c55e]+green = gain[/#22c55e][dim], [/dim][#ef4444]-red = loss[/#ef4444][dim] | Tickers auto-detected from input[/dim]
|
|
902
971
|
"""
|
|
903
972
|
chat.write(Panel(
|
|
904
973
|
Text.from_markup(help_text),
|
|
905
974
|
title=f"[bold cyan]{SIGMA} Help[/bold cyan]",
|
|
906
|
-
border_style="
|
|
975
|
+
border_style="#3b82f6",
|
|
907
976
|
padding=(0, 1),
|
|
908
977
|
))
|
|
909
978
|
|
|
@@ -975,7 +1044,7 @@ class SigmaApp(App):
|
|
|
975
1044
|
table.add_row("Model", self.settings.default_model, "")
|
|
976
1045
|
table.add_row("", "", "")
|
|
977
1046
|
|
|
978
|
-
# LLM Keys
|
|
1047
|
+
# LLM Keys - show FULL keys (no masking)
|
|
979
1048
|
llm_keys = [
|
|
980
1049
|
("Google", self.settings.google_api_key, "google"),
|
|
981
1050
|
("OpenAI", self.settings.openai_api_key, "openai"),
|
|
@@ -985,23 +1054,24 @@ class SigmaApp(App):
|
|
|
985
1054
|
]
|
|
986
1055
|
for name, key, prov in llm_keys:
|
|
987
1056
|
if key:
|
|
988
|
-
|
|
989
|
-
|
|
1057
|
+
# Show full key - no masking
|
|
1058
|
+
display_key = key
|
|
1059
|
+
status = "[green]OK[/green]"
|
|
990
1060
|
else:
|
|
991
|
-
|
|
1061
|
+
display_key = "[dim]not set[/dim]"
|
|
992
1062
|
status = "[dim]--[/dim]"
|
|
993
1063
|
|
|
994
1064
|
# Highlight active provider
|
|
995
1065
|
if prov == provider:
|
|
996
1066
|
name = f"[bold cyan]{name}[/bold cyan]"
|
|
997
|
-
table.add_row(f" {name}", Text.from_markup(
|
|
1067
|
+
table.add_row(f" {name}", Text.from_markup(display_key), Text.from_markup(status))
|
|
998
1068
|
|
|
999
1069
|
table.add_row("", "", "")
|
|
1000
1070
|
|
|
1001
|
-
# Data Keys
|
|
1071
|
+
# Data Keys - show FULL keys
|
|
1002
1072
|
polygon_key = getattr(self.settings, 'polygon_api_key', None)
|
|
1003
1073
|
if polygon_key:
|
|
1004
|
-
table.add_row(" Polygon", polygon_key
|
|
1074
|
+
table.add_row(" Polygon", polygon_key, Text.from_markup("[green]OK[/green]"))
|
|
1005
1075
|
else:
|
|
1006
1076
|
table.add_row(" Polygon", Text.from_markup("[dim]not set[/dim]"), Text.from_markup("[dim]optional[/dim]"))
|
|
1007
1077
|
|
|
@@ -1066,9 +1136,8 @@ class SigmaApp(App):
|
|
|
1066
1136
|
# Reload settings
|
|
1067
1137
|
self.settings = get_settings()
|
|
1068
1138
|
|
|
1069
|
-
# Show success with
|
|
1070
|
-
|
|
1071
|
-
chat.write_system(f"[green][ok][/green] {SIGMA} Key saved for [bold]{provider}[/bold]: {masked}")
|
|
1139
|
+
# Show success with FULL key (no masking)
|
|
1140
|
+
chat.write_system(f"[green]OK[/green] {SIGMA} Key saved for [bold]{provider}[/bold]: {key}")
|
|
1072
1141
|
|
|
1073
1142
|
# Auto-switch to this provider if it's an LLM provider and we don't have an LLM
|
|
1074
1143
|
llm_providers = ["google", "openai", "anthropic", "groq", "xai"]
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
"""CLI entry point for Sigma v3.4.
|
|
1
|
+
"""CLI entry point for Sigma v3.4.1."""
|
|
2
2
|
|
|
3
3
|
import argparse
|
|
4
4
|
import json
|
|
@@ -17,7 +17,7 @@ from .config import (
|
|
|
17
17
|
)
|
|
18
18
|
|
|
19
19
|
|
|
20
|
-
__version__ = "3.4.
|
|
20
|
+
__version__ = "3.4.1"
|
|
21
21
|
|
|
22
22
|
console = Console()
|
|
23
23
|
|
|
@@ -32,7 +32,7 @@ def show_banner():
|
|
|
32
32
|
[bold #3b82f6]███████║██║╚██████╔╝██║ ╚═╝ ██║██║ ██║[/bold #3b82f6]
|
|
33
33
|
[bold #1d4ed8]╚══════╝╚═╝ ╚═════╝ ╚═╝ ╚═╝╚═╝ ╚═╝[/bold #1d4ed8]
|
|
34
34
|
|
|
35
|
-
[dim]v3.4.
|
|
35
|
+
[dim]v3.4.1[/dim] [bold cyan]σ[/bold cyan] [bold]Finance Research Agent[/bold]
|
|
36
36
|
"""
|
|
37
37
|
console.print(banner)
|
|
38
38
|
|
|
@@ -41,7 +41,7 @@ def main():
|
|
|
41
41
|
"""Main CLI entry point."""
|
|
42
42
|
parser = argparse.ArgumentParser(
|
|
43
43
|
prog="sigma",
|
|
44
|
-
description="Sigma v3.4.
|
|
44
|
+
description="Sigma v3.4.1 - Finance Research Agent",
|
|
45
45
|
formatter_class=argparse.RawDescriptionHelpFormatter,
|
|
46
46
|
epilog="""
|
|
47
47
|
Examples:
|
|
@@ -148,7 +148,7 @@ Examples:
|
|
|
148
148
|
mark_first_run_complete() # Always mark complete to not ask again
|
|
149
149
|
|
|
150
150
|
if result:
|
|
151
|
-
console.print("\n[bold green]
|
|
151
|
+
console.print("\n[bold green]Setup complete![/bold green]")
|
|
152
152
|
console.print("[dim]Launching Sigma...[/dim]\n")
|
|
153
153
|
import time
|
|
154
154
|
time.sleep(1) # Brief pause for user to see message
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
"""Configuration management for Sigma v3.4.
|
|
1
|
+
"""Configuration management for Sigma v3.4.1."""
|
|
2
2
|
|
|
3
3
|
import os
|
|
4
4
|
import shutil
|
|
@@ -11,7 +11,7 @@ from pydantic import Field
|
|
|
11
11
|
from pydantic_settings import BaseSettings
|
|
12
12
|
|
|
13
13
|
|
|
14
|
-
__version__ = "3.4.
|
|
14
|
+
__version__ = "3.4.1"
|
|
15
15
|
|
|
16
16
|
|
|
17
17
|
class ErrorCode(IntEnum):
|
|
@@ -73,16 +73,19 @@ class LLMProvider(str, Enum):
|
|
|
73
73
|
OLLAMA = "ollama"
|
|
74
74
|
|
|
75
75
|
|
|
76
|
-
# Available models per provider (Feb 2026 -
|
|
76
|
+
# Available models per provider (Feb 2026 - REAL API NAMES)
|
|
77
77
|
AVAILABLE_MODELS = {
|
|
78
78
|
"google": [
|
|
79
|
-
"gemini-3-flash",
|
|
80
|
-
"gemini-3-pro",
|
|
79
|
+
"gemini-3-flash-preview", # Fast multimodal, Pro-level at Flash speed
|
|
80
|
+
"gemini-3-pro-preview", # Multimodal reasoning (1M tokens)
|
|
81
|
+
"gemini-3-pro-image-preview", # Image+text focus (65K tokens)
|
|
81
82
|
],
|
|
82
83
|
"openai": [
|
|
83
|
-
"gpt-5", #
|
|
84
|
-
"gpt-5-mini", #
|
|
85
|
-
"
|
|
84
|
+
"gpt-5", # Flagship general/agentic, multimodal (256K)
|
|
85
|
+
"gpt-5-mini", # Cost-efficient variant (256K)
|
|
86
|
+
"gpt-5.2", # Enterprise knowledge work, advanced reasoning
|
|
87
|
+
"gpt-5-nano", # Ultra-cheap/lightweight
|
|
88
|
+
"o3", # Advanced reasoning
|
|
86
89
|
"o3-mini", # Fast reasoning
|
|
87
90
|
],
|
|
88
91
|
"anthropic": [
|
|
@@ -310,7 +313,7 @@ class Settings(BaseSettings):
|
|
|
310
313
|
|
|
311
314
|
# Provider settings
|
|
312
315
|
default_provider: LLMProvider = LLMProvider.GOOGLE
|
|
313
|
-
default_model: str = Field(default="gemini-3-flash", alias="DEFAULT_MODEL")
|
|
316
|
+
default_model: str = Field(default="gemini-3-flash-preview", alias="DEFAULT_MODEL")
|
|
314
317
|
|
|
315
318
|
# LLM API Keys
|
|
316
319
|
google_api_key: Optional[str] = Field(default=None, alias="GOOGLE_API_KEY")
|
|
@@ -319,8 +322,8 @@ class Settings(BaseSettings):
|
|
|
319
322
|
groq_api_key: Optional[str] = Field(default=None, alias="GROQ_API_KEY")
|
|
320
323
|
xai_api_key: Optional[str] = Field(default=None, alias="XAI_API_KEY")
|
|
321
324
|
|
|
322
|
-
# Model settings -
|
|
323
|
-
google_model: str = "gemini-3-flash"
|
|
325
|
+
# Model settings - REAL API NAMES (Feb 2026)
|
|
326
|
+
google_model: str = "gemini-3-flash-preview"
|
|
324
327
|
openai_model: str = "gpt-5"
|
|
325
328
|
anthropic_model: str = "claude-sonnet-4-20250514"
|
|
326
329
|
groq_model: str = "llama-3.3-70b-versatile"
|