QAway-to commited on
Commit
eadb379
·
1 Parent(s): 90eebc8

Back to old version.

Browse files
Files changed (1) hide show
  1. app.py +176 -107
app.py CHANGED
@@ -12,115 +12,184 @@ analyzer = PortfolioAnalyzer(llm_service, MODEL_NAME)
12
  comparer = PortfolioComparer(llm_service, MODEL_NAME)
13
  chatbot = ChatAssistant(llm_service, MODEL_NAME)
14
 
15
- # === Text dictionaries for RU/ENG ===
16
- LANG_TEXT = {
17
- "ENG": {
18
- "title": "🧠 Investment Portfolio Analysis",
19
- "tabs": ["📊 Analysis", "⚖️ Comparison", "💬 Chat2", "📋 Metrics Table", "📈 AlphaBTC Chart"],
20
- "labels": {
21
- "analyze_input": "Enter portfolioId or link",
22
- "analyze_button": "🔍 Analyze",
23
- "analyze_output": "Analysis Result",
24
- "compare_1": "Portfolio A",
25
- "compare_2": "Portfolio B",
26
- "compare_button": "📈 Compare",
27
- "compare_output": "Comparison Result",
28
- "chat_input": "Ask your question",
29
- "chat_button": "Send",
30
- "chat_output": "Response",
31
- "metrics_input": "Enter portfolioId",
32
- "metrics_button": "Show Metrics",
33
- "metrics_output": "Portfolio Metrics",
34
- "chart_input": "Enter portfolioId",
35
- "chart_button": "Plot Chart",
36
- "chart_output": "Alpha to BTC Chart",
37
- }
38
- },
39
- "RU": {
40
- "title": "🧠 Анализ инвестиционных портфелей",
41
- "tabs": ["📊 Анализ", "⚖️ Сравнение", "💬 Диалог", "📋 Таблица метрик", "📈 График AlphaBTC"],
42
- "labels": {
43
- "analyze_input": "Введите ссылку или portfolioId",
44
- "analyze_button": "🔍 Проанализировать",
45
- "analyze_output": "📈 Результат анализа",
46
- "compare_1": "Портфель 1",
47
- "compare_2": "Портфель 2",
48
- "compare_button": "📊 Сравнить",
49
- "compare_output": "📉 Результат сравнения",
50
- "chat_input": "Ваш вопрос",
51
- "chat_button": "Отправить",
52
- "chat_output": "Ответ",
53
- "metrics_input": "Введите portfolioId",
54
- "metrics_button": "📥 Показать метрики",
55
- "metrics_output": "📊 Метрики портфеля",
56
- "chart_input": "Введите portfolioId",
57
- "chart_button": "Построить график",
58
- "chart_output": "График Alpha к BTC",
59
- }
60
- }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
61
  }
62
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
63
 
64
- def build_interface(lang="ENG"):
65
- text = LANG_TEXT[lang]
66
-
67
- with gr.Blocks(theme=gr.themes.Soft()) as demo:
68
- lang_state = gr.State(lang)
69
-
70
- # Header
71
- gr.Markdown(f"## {text['title']}")
72
-
73
- # Language toggle
74
- lang_button = gr.Button("🌐 Switch Language (RU / ENG)")
75
-
76
- def switch_language(current_lang):
77
- return "RU" if current_lang == "ENG" else "ENG"
78
-
79
- lang_button.click(fn=switch_language, inputs=lang_state, outputs=lang_state).then(
80
- fn=lambda l: gr.update(visible=False), inputs=lang_state, outputs=None
81
- )
82
-
83
- with gr.Tabs():
84
- # --- Tab 1: Analysis ---
85
- with gr.TabItem(text["tabs"][0]):
86
- inp = gr.Textbox(label=text["labels"]["analyze_input"])
87
- btn = gr.Button(text["labels"]["analyze_button"])
88
- out = gr.Textbox(label=text["labels"]["analyze_output"], lines=15)
89
- btn.click(fn=analyzer.run, inputs=inp, outputs=out)
90
-
91
- # --- Tab 2: Comparison ---
92
- with gr.TabItem(text["tabs"][1]):
93
- a = gr.Textbox(label=text["labels"]["compare_1"])
94
- b = gr.Textbox(label=text["labels"]["compare_2"])
95
- cmp_btn = gr.Button(text["labels"]["compare_button"])
96
- cmp_out = gr.Textbox(label=text["labels"]["compare_output"], lines=20)
97
- cmp_btn.click(fn=comparer.run, inputs=[a, b], outputs=cmp_out)
98
-
99
- # --- Tab 3: Chat ---
100
- with gr.TabItem(text["tabs"][2]):
101
- chat_in = gr.Textbox(label=text["labels"]["chat_input"])
102
- chat_btn = gr.Button(text["labels"]["chat_button"])
103
- chat_out = gr.Textbox(label=text["labels"]["chat_output"], lines=8)
104
- chat_btn.click(fn=chatbot.run, inputs=chat_in, outputs=chat_out)
105
-
106
- # --- Tab 4: Metrics Table ---
107
- with gr.TabItem(text["tabs"][3]):
108
- mid = gr.Textbox(label=text["labels"]["metrics_input"])
109
- mbtn = gr.Button(text["labels"]["metrics_button"])
110
- mout = gr.Dataframe(label=text["labels"]["metrics_output"], wrap=True)
111
- mbtn.click(fn=show_metrics_table, inputs=mid, outputs=mout)
112
-
113
- # --- Tab 5: AlphaBTC Chart ---
114
- with gr.TabItem(text["tabs"][4]):
115
- cid = gr.Textbox(label=text["labels"]["chart_input"], value="3852a354-e66e-4bc5-97e9-55124e31e687")
116
- cbtn = gr.Button(text["labels"]["chart_button"])
117
- cout = gr.Plot(label=text["labels"]["chart_output"])
118
- cbtn.click(fn=build_alpha_chart, inputs=cid, outputs=cout)
119
-
120
- return demo
121
-
122
-
123
- # === Default launch in English ===
124
  if __name__ == "__main__":
125
- demo = build_interface(lang="ENG")
126
  demo.launch()
 
12
  comparer = PortfolioComparer(llm_service, MODEL_NAME)
13
  chatbot = ChatAssistant(llm_service, MODEL_NAME)
14
 
15
+ # === Bloomberg-style dark theme ===
16
+ dark_theme = gr.themes.Base(
17
+ primary_hue="violet",
18
+ secondary_hue="gray",
19
+ neutral_hue="zinc",
20
+ ).set(
21
+ body_background_fill="#0d1117", # main background (dark navy)
22
+ body_text_color="#e6edf3", # main text
23
+ block_background_fill="#161b22", # card background
24
+ block_border_color="#30363d", # subtle border
25
+ button_primary_background_fill="#4f46e5",# indigo-violet accent
26
+ button_primary_background_fill_hover="#6366f1",
27
+ button_primary_text_color="#ffffff",
28
+ input_background_fill="#0d1117",
29
+ block_shadow="0 2px 6px rgba(0,0,0,0.3)",
30
+ block_label_text_color="#9da5b4",
31
+ block_label_text_size="sm",
32
+ )
33
+
34
+ with gr.Blocks(theme=dark_theme, css="""
35
+ /* === Bloomberg / Dark Finance Style === */
36
+ .gradio-container {
37
+ max-width: 1000px !important;
38
+ margin: auto !important;
39
+ font-family: 'Inter', sans-serif;
40
+ background-color: #0d1117 !important;
41
+ }
42
+ /* === LLM Commentary Styling === */
43
+ #llm_comment_box textarea {
44
+ max-height: 420px !important; /* ограничение высоты */
45
+ overflow-y: auto !important; /* вертикальный скроллинг */
46
+ background-color: #161b22 !important;
47
+ color: #f0f6fc !important;
48
+ border: 1px solid #30363d !important;
49
+ border-radius: 6px !important;
50
+ font-family: 'JetBrains Mono', monospace !important;
51
+ font-size: 14px !important;
52
+ line-height: 1.5 !important;
53
+ padding: 12px !important;
54
+ }
55
+ /* === Comparison Table === */
56
+ #comparison_table {
57
+ margin-top: 8px !important;
58
+ }
59
+ #1
60
+ h2, h3, .gr-markdown {
61
+ font-weight: 600;
62
+ color: #f0f6fc !important;
63
+ }
64
+ .gr-button {
65
+ border-radius: 6px !important;
66
+ font-weight: 600 !important;
67
+ letter-spacing: 0.3px;
68
+ box-shadow: 0 2px 4px rgba(0,0,0,0.25);
69
+ }
70
+ .gr-textbox, .gr-dataframe {
71
+ border-radius: 6px !important;
72
+ }
73
+ .gr-button.primary {
74
+ background: linear-gradient(90deg, #6366f1, #4f46e5);
75
+ border: none !important;
76
+ }
77
+ .gr-tab {
78
+ background-color: #161b22 !important;
79
+ color: #c9d1d9 !important;
80
+ }
81
+ .gr-tabs {
82
+ border-bottom: 1px solid #30363d !important;
83
+ }
84
+ .gr-plot {
85
+ background: #0d1117 !important;
86
+ }
87
+ /* Fix Gradio plot overlay */
88
+ #alpha_chart svg {
89
+ display: none !important;
90
+ }
91
+ #alpha_chart .wrap {
92
+ background: transparent !important;
93
+ box-shadow: none !important;
94
+ }
95
+ /* === Styled comparison table === */
96
+ .gr-dataframe table {
97
+ border-collapse: collapse !important;
98
+ width: 100% !important;
99
+ color: #c9d1d9 !important;
100
+ background-color: #161b22 !important;
101
+ }
102
+ .gr-dataframe th {
103
+ background-color: #21262d !important;
104
+ color: #f0f6fc !important;
105
+ font-weight: 600 !important;
106
+ text-transform: uppercase;
107
+ border-bottom: 1px solid #30363d !important;
108
+ }
109
+ .gr-dataframe td {
110
+ border-top: 1px solid #30363d !important;
111
+ padding: 8px !important;
112
  }
113
 
114
+ """) as demo:
115
+ gr.Markdown("## Investment Portfolio Analyzer")
116
+ gr.Markdown(
117
+ "A professional dashboard for analyzing and comparing investment portfolios using AI insights.",
118
+ elem_classes="subtitle",
119
+ )
120
+
121
+ with gr.Tabs():
122
+ # --- Analysis Tab ---
123
+ with gr.TabItem("Analysis"):
124
+ portfolio_input = gr.Textbox(
125
+ label="Portfolio ID or Link",
126
+ placeholder="Enter a portfolio ID (e.g. ea856c1b-...)",
127
+ lines=1,
128
+ value='b1ef37aa-5b9a-41b4-9394-8823f2de36bb',
129
+ )
130
+ analyze_button = gr.Button("Run Analysis", variant="primary")
131
+ analyze_output = gr.Textbox(label="Analysis Result", lines=15)
132
+ analyze_button.click(fn=analyzer.run, inputs=portfolio_input, outputs=analyze_output)
133
+
134
+ # --- Comparison Table Tab ---
135
+ with gr.TabItem("Comparison Table"):
136
+ comp_input_1 = gr.Textbox(label="Portfolio A", value="3852a354-e66e-4bc5-97e9-55124e31e687")
137
+ comp_input_2 = gr.Textbox(label="Portfolio B", value="b1ef37aa-5b9a-41b4-9394-8823f2de36bb")
138
+ comp_button = gr.Button("Load Comparison", variant="primary")
139
+
140
+ # комментарий теперь над таблицей
141
+ comp_output_comment = gr.Textbox(
142
+ label="AI Commentary",
143
+ lines=8,
144
+ interactive=True,
145
+ show_copy_button=True,
146
+ elem_id="llm_comment_box",
147
+ )
148
+
149
+ comp_output_table = gr.Dataframe(
150
+ label="Comparative Metrics",
151
+ wrap=True,
152
+ elem_id="comparison_table",
153
+ )
154
+
155
+ from core.comparison_table import show_comparison_table
156
+
157
+ comp_button.click(
158
+ fn=show_comparison_table,
159
+ inputs=[comp_input_1, comp_input_2],
160
+ outputs=[comp_output_table, comp_output_comment],
161
+ )
162
+
163
+ # --- Chat Assistant Tab ---
164
+ with gr.TabItem("Assistant"):
165
+ chat_input = gr.Textbox(label="Ask about investments or analysis")
166
+ chat_button = gr.Button("Send Question", variant="primary")
167
+ chat_output = gr.Textbox(label="AI Response", lines=8)
168
+ chat_button.click(fn=chatbot.run, inputs=chat_input, outputs=chat_output)
169
+
170
+ # --- Metrics Table Tab ---
171
+ with gr.TabItem("Metrics Table"):
172
+ metrics_input = gr.Textbox(label="Portfolio ID", value='b1ef37aa-5b9a-41b4-9394-8823f2de36bb')
173
+ metrics_button = gr.Button("Load Metrics", variant="primary")
174
+ metrics_output = gr.Dataframe(label="Portfolio Metrics", wrap=True)
175
+ metrics_button.click(fn=show_metrics_table, inputs=metrics_input, outputs=metrics_output)
176
+
177
+ # --- AlphaBTC Chart Tab (fixed overlay) ---
178
+ with gr.TabItem("AlphaBTC Chart"):
179
+ chart_input = gr.Textbox(label="Portfolio ID", value="3852a354-e66e-4bc5-97e9-55124e31e687")
180
+ chart_button = gr.Button("Generate Chart", variant="primary")
181
+ chart_output = gr.Plot(
182
+ label="Alpha vs BTC",
183
+ show_label=False,
184
+ elem_id="alpha_chart",
185
+ )
186
+ chart_button.click(fn=build_alpha_chart, inputs=chart_input, outputs=chart_output)
187
+
188
+ gr.Markdown("---")
189
+ gr.Markdown(
190
+ "<center><small style='color:#6e7681;'>Developed with Featherless.ai • Powered by OpenAI-compatible API</small></center>",
191
+ elem_classes="footer",
192
+ )
193
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
194
  if __name__ == "__main__":
 
195
  demo.launch()