aipa-cli 0.1.4__tar.gz → 0.1.6__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.
Files changed (43) hide show
  1. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/CHANGELOG.md +19 -0
  2. aipa_cli-0.1.6/PKG-INFO +260 -0
  3. aipa_cli-0.1.6/README.md +235 -0
  4. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/__init__.py +1 -1
  5. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/app.py +15 -2
  6. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/chat.py +15 -1
  7. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/cli.py +19 -1
  8. aipa_cli-0.1.6/src/aipriceaction_terminal/cli_setup.py +71 -0
  9. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/settings_tab.py +7 -2
  10. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/user_settings.py +1 -0
  11. aipa_cli-0.1.4/PKG-INFO +0 -73
  12. aipa_cli-0.1.4/README.md +0 -48
  13. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/.gitignore +0 -0
  14. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/LICENSE +0 -0
  15. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/pyproject.toml +0 -0
  16. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/__main__.py +0 -0
  17. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/actions.py +0 -0
  18. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/agents/__init__.py +0 -0
  19. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/agents/agent.py +0 -0
  20. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/agents/callbacks.py +0 -0
  21. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/agents/config.py +0 -0
  22. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/agents/personas.py +0 -0
  23. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/agents/tools.py +0 -0
  24. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/bindings.py +0 -0
  25. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/cli_commands.py +0 -0
  26. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/deep_research.py +0 -0
  27. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/theme.py +0 -0
  28. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/ticker_data.py +0 -0
  29. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/utils.py +0 -0
  30. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/widgets/__init__.py +0 -0
  31. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/widgets/chat_input.py +0 -0
  32. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/widgets/ticker_select.py +0 -0
  33. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/src/aipriceaction_terminal/workflows.py +0 -0
  34. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/conftest.py +0 -0
  35. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/openrouter_responses.py +0 -0
  36. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/test_app.py +0 -0
  37. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/test_chat.py +0 -0
  38. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/test_integration.py +0 -0
  39. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/test_settings_api.py +0 -0
  40. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/test_thinking.py +0 -0
  41. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/test_tool_call_streaming.py +0 -0
  42. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/test_utils.py +0 -0
  43. {aipa_cli-0.1.4 → aipa_cli-0.1.6}/tests/test_workflows.py +0 -0
@@ -5,6 +5,25 @@ All notable changes to this project will be documented in this file.
5
5
  The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
6
6
  and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
7
 
8
+ ## [0.1.6] - 2026-05-09
9
+
10
+ ### Added
11
+ - Add `aipa setup` interactive CLI command for first-run configuration (language, reference ticker, API key, base URL, model)
12
+ - Add `setup_done` flag to user settings, auto-run setup before commands that need an API key (`analyze`, `deep-research`, TUI)
13
+ - Add "First-Run Setup" section to README documenting which commands require setup
14
+
15
+ ### Changed
16
+ - Lazy-load `AgentSession` in TUI instead of creating on mount, preventing crash when no API key is configured
17
+ - Guard agent usage in chat (`_run_agent_chat`, `_run_analyze`, `/clear`) and settings tab with `_ensure_agent()`
18
+
19
+ ### Fixed
20
+ - Fix crash on `aipa` launch when no API key is configured (`OpenAIError: Missing credentials`)
21
+
22
+ ## [0.1.5] - 2026-05-09
23
+
24
+ ### Changed
25
+ - Expand README with Quick Start examples, full CLI reference for all commands, TUI slash commands, and configuration documentation
26
+
8
27
  ## [0.1.4] - 2026-05-09
9
28
 
10
29
  ### Added
@@ -0,0 +1,260 @@
1
+ Metadata-Version: 2.4
2
+ Name: aipa-cli
3
+ Version: 0.1.6
4
+ Summary: Terminal TUI for AI-powered ticker analysis
5
+ Project-URL: Homepage, https://github.com/quanhua92/aipriceaction
6
+ Project-URL: Repository, https://github.com/quanhua92/aipriceaction
7
+ Author-email: Quan Hua <quanhua92@gmail.com>
8
+ License-Expression: MIT
9
+ License-File: LICENSE
10
+ Classifier: Development Status :: 3 - Alpha
11
+ Classifier: Environment :: Console :: Curses
12
+ Classifier: Intended Audience :: Financial and Insurance Industry
13
+ Classifier: License :: OSI Approved :: MIT License
14
+ Classifier: Programming Language :: Python :: 3
15
+ Classifier: Programming Language :: Python :: 3.13
16
+ Classifier: Topic :: Office/Business :: Financial
17
+ Requires-Python: >=3.13
18
+ Requires-Dist: aipriceaction>=0.1.9
19
+ Requires-Dist: langchain-core
20
+ Requires-Dist: langchain-openai
21
+ Requires-Dist: langgraph
22
+ Requires-Dist: textual-autocomplete>=4.0.6
23
+ Requires-Dist: textual>=3.0.0
24
+ Description-Content-Type: text/markdown
25
+
26
+ # AIPA Terminal
27
+
28
+ **Live site:** [aipriceaction.com](https://aipriceaction.com) | **GitHub:** [aipriceaction](https://github.com/quanhua92/aipriceaction) | **Frontend:** [aipriceaction-web](https://github.com/quanhua92/aipriceaction-web) | **Docker image:** [`quanhua92/aipriceaction:latest`](https://hub.docker.com/r/quanhua92/aipriceaction) | **Python SDK:** [`aipriceaction` on PyPI](https://pypi.org/project/aipriceaction/) | **AIPA Terminal:** [`aipa-cli` on PyPI](https://pypi.org/project/aipa-cli/)
29
+
30
+ Textual-based terminal interface for AI-powered ticker analysis. Features streaming chat with thinking/reasoning display, autocomplete, slash commands, and workflow tabs.
31
+
32
+ ## Install
33
+
34
+ ```bash
35
+ # Run directly (no install)
36
+ uvx aipa-cli
37
+
38
+ # Or install as a standalone tool
39
+ uv tool install aipa-cli
40
+
41
+ # Use either command
42
+ aipa
43
+ aipa-cli
44
+ ```
45
+
46
+ ## Requirements
47
+
48
+ - Python 3.13+
49
+ - An OpenAI-compatible API key (`OPENAI_API_KEY`) — only needed for AI analysis, not for data fetching
50
+ - Optional: set `OPENAI_BASE_URL` for custom providers like OpenRouter
51
+
52
+ ## Quick Start
53
+
54
+ ```bash
55
+ # Launch the TUI — first run auto-starts interactive setup
56
+ aipa
57
+
58
+ # Or run setup manually at any time
59
+ aipa setup
60
+
61
+ # AI analysis with default question template
62
+ aipa analyze VCB
63
+
64
+ # AI analysis with a custom question
65
+ aipa analyze VCB --question "What is the support level and stop loss?"
66
+
67
+ # Browse available question templates
68
+ aipa analyze VCB --questions
69
+
70
+ # Use a specific question template by index
71
+ aipa analyze VCB 2 --question "What is the current trend of VCB?"
72
+
73
+ # Dump raw context data without calling the LLM (no API key needed)
74
+ aipa analyze VCB --context-only
75
+
76
+ # Override language to English (default is your saved setting)
77
+ aipa analyze VCB --lang en
78
+
79
+ # Use hourly interval with SMA instead of EMA
80
+ aipa analyze BTCUSDT --interval 1h --ma-type sma
81
+
82
+ # Analyze multiple tickers at once
83
+ aipa analyze VCB FPT VIC --interval 1D
84
+
85
+ # Run multi-agent deep research pipeline
86
+ aipa deep-research
87
+
88
+ # Deep research with a custom question and save report to file
89
+ aipa deep-research "Which sectors are leading the market?" --output report.md
90
+
91
+ # Resume a previous deep-research session from checkpoint
92
+ aipa deep-research --resume <session-id>
93
+
94
+ # Fetch raw OHLCV data as a table
95
+ aipa get-ohlcv-data VCB --interval 1D --limit 10
96
+
97
+ # Fetch with date range and no moving averages
98
+ aipa get-ohlcv-data VCB --start-date 2026-04-01 --end-date 2026-04-30 --no-ma
99
+ ```
100
+
101
+ ## CLI Commands
102
+
103
+ ### `aipa analyze`
104
+
105
+ AI-powered analysis for one or more tickers. Builds context from OHLCV data and sends it to the LLM with a question.
106
+
107
+ ```
108
+ # Default: uses question template 0 with your saved language setting
109
+ aipa analyze VCB
110
+
111
+ # Custom question
112
+ aipa analyze VCB --question "Is this a good time to buy?"
113
+
114
+ # List all question templates (trading opportunity, news, Wyckoff, etc.)
115
+ aipa analyze VCB --questions
116
+
117
+ # Raw data dump only (no LLM call, no API key required)
118
+ aipa analyze VCB --context-only
119
+
120
+ # Multi-ticker analysis
121
+ aipa analyze VCB FPT MBB
122
+
123
+ # Hourly data with SMA indicators
124
+ aipa analyze VCB --interval 1h --ma-type sma --limit 50
125
+
126
+ # Force English output
127
+ aipa analyze VCB --lang en
128
+ ```
129
+
130
+ | Flag | Description |
131
+ |---|---|
132
+ | `--question TEXT` | Custom analysis question |
133
+ | `--questions` | List available question templates and exit |
134
+ | `--context-only` | Dump raw context without LLM (no API key needed) |
135
+ | `--interval` | Time interval: `1m`, `5m`, `15m`, `30m`, `1h`, `4h`, `1D`, `1W` (default: `1D`) |
136
+ | `--limit N` | Number of bars (default: 20) |
137
+ | `--source` | Filter by source: `vn` or `crypto` |
138
+ | `--start-date` / `--end-date` | Date range (e.g. `2026-04-01`) |
139
+ | `--reference-ticker` | Reference ticker for market context (default: `VNINDEX`) |
140
+ | `--lang` | Language: `en` or `vn` (default: saved setting) |
141
+ | `--ma-type` | Moving average type: `ema` or `sma` (default: `ema`) |
142
+
143
+ ### `aipa deep-research`
144
+
145
+ Multi-agent deep research pipeline: supervisor decomposes into sector subtasks, parallel workers fetch data and analyze, aggregator synthesizes, and reviewer validates data integrity.
146
+
147
+ ```
148
+ # Default: comprehensive market overview with all VN sectors
149
+ aipa deep-research
150
+
151
+ # Custom research question
152
+ aipa deep-research "Compare banking vs real estate sectors"
153
+
154
+ # Save final report to file
155
+ aipa deep-research --output ~/reports/market-analysis.md
156
+
157
+ # Resume from a previous checkpoint session
158
+ aipa deep-research --resume 019e0cbb-0466-fa9f-d68c-2da40d35a68f
159
+
160
+ # Force Vietnamese output
161
+ aipa deep-research --lang vn
162
+ ```
163
+
164
+ | Flag | Description |
165
+ |---|---|
166
+ | `--resume ID` | Resume from a checkpoint session ID |
167
+ | `--output FILE` | Save final report to file |
168
+ | `--lang` | Language: `en` or `vn` (default: saved setting) |
169
+
170
+ ### `aipa get-ohlcv-data`
171
+
172
+ Fetch raw OHLCV data as a table (no LLM involved, works without setup).
173
+
174
+ ```
175
+ # Default: daily data with EMA indicators
176
+ aipa get-ohlcv-data VCB
177
+
178
+ # Hourly data, last 10 bars
179
+ aipa get-ohlcv-data VCB --interval 1h --limit 10
180
+
181
+ # Date range, no moving averages
182
+ aipa get-ohlcv-data VCB --start-date 2026-04-01 --end-date 2026-04-30 --no-ma
183
+
184
+ # Crypto data
185
+ aipa get-ohlcv-data BTCUSDT --interval 1D --limit 30
186
+ ```
187
+
188
+ | Flag | Description |
189
+ |---|---|
190
+ | `--interval` | Time interval (default: `1D`) |
191
+ | `--limit N` | Number of bars |
192
+ | `--start-date` / `--end-date` | Date range |
193
+ | `--source` | Filter by source: `vn` or `crypto` |
194
+ | `--ma` / `--no-ma` | Include/exclude moving averages (default: included) |
195
+ | `--ema` | Use EMA instead of SMA |
196
+
197
+ ### `aipa setup`
198
+
199
+ Interactive first-run configuration. Prompts for language, reference ticker, API key, base URL, and model. Settings are saved to `~/.aipriceaction/settings.json`. Re-running shows current values as defaults.
200
+
201
+ ```
202
+ # Run interactively
203
+ aipa setup
204
+ ```
205
+
206
+ ## First-Run Setup
207
+
208
+ Commands that require an API key will auto-run `aipa setup` on first use if not yet configured. Commands that don't need an API key always work immediately.
209
+
210
+ | Command | Setup required? |
211
+ |---|---|
212
+ | `aipa get-ohlcv-data` | No setup needed |
213
+ | `aipa analyze VCB --context-only` | No setup needed |
214
+ | `aipa analyze VCB --questions` | No setup needed |
215
+ | `aipa setup` | Runs setup |
216
+ | `aipa` | Auto-runs setup first |
217
+ | `aipa analyze VCB` | Auto-runs setup first |
218
+ | `aipa deep-research` | Auto-runs setup first |
219
+
220
+ ## TUI
221
+
222
+ Launch the TUI with `aipa`. The interface has three tabs:
223
+
224
+ - **Chat** — AI-powered chat with streaming responses, thinking/reasoning display, slash commands, and arrow-key history navigation
225
+ - **Workflows** — Structured analysis forms with question bank dropdown for ticker analysis and deep research
226
+ - **Tickers** — Browse and search available tickers
227
+
228
+ ### Slash Commands (Chat tab)
229
+
230
+ ```
231
+ /analyze VCB # Default AI analysis
232
+ /analyze VCB 1h # AI analysis with hourly interval
233
+ /analyze VCB 2 # Use question template index 2
234
+ /analyze VCB --question What is support? # Custom question
235
+ /export VCB FPT # Export context to markdown file
236
+ /deep-research # Multi-agent research
237
+ /clear # Clear chat history
238
+ /exit # Quit
239
+ ```
240
+
241
+ Press `Ctrl+O` in the Chat tab to view thinking/reasoning history.
242
+
243
+ ### Settings Tab
244
+
245
+ Configure your API key, model, and base URL directly in the TUI. Settings are saved to `~/.aipriceaction/settings.json` and shared across both TUI and CLI.
246
+
247
+ ## Configuration
248
+
249
+ Settings are loaded from `~/.aipriceaction/settings.json`. You can configure them via the TUI Settings tab or set environment variables:
250
+
251
+ | Variable | Description | Default |
252
+ |---|---|---|
253
+ | `OPENAI_API_KEY` | API key for the LLM provider | — |
254
+ | `OPENAI_BASE_URL` | Base URL for OpenAI-compatible API | OpenRouter |
255
+ | `OPENAI_MODEL` | Model name | `openrouter/owl-alpha` |
256
+ | `DATABASE_URL` | Backend API URL | `http://localhost:3000` |
257
+
258
+ ## License
259
+
260
+ MIT
@@ -0,0 +1,235 @@
1
+ # AIPA Terminal
2
+
3
+ **Live site:** [aipriceaction.com](https://aipriceaction.com) | **GitHub:** [aipriceaction](https://github.com/quanhua92/aipriceaction) | **Frontend:** [aipriceaction-web](https://github.com/quanhua92/aipriceaction-web) | **Docker image:** [`quanhua92/aipriceaction:latest`](https://hub.docker.com/r/quanhua92/aipriceaction) | **Python SDK:** [`aipriceaction` on PyPI](https://pypi.org/project/aipriceaction/) | **AIPA Terminal:** [`aipa-cli` on PyPI](https://pypi.org/project/aipa-cli/)
4
+
5
+ Textual-based terminal interface for AI-powered ticker analysis. Features streaming chat with thinking/reasoning display, autocomplete, slash commands, and workflow tabs.
6
+
7
+ ## Install
8
+
9
+ ```bash
10
+ # Run directly (no install)
11
+ uvx aipa-cli
12
+
13
+ # Or install as a standalone tool
14
+ uv tool install aipa-cli
15
+
16
+ # Use either command
17
+ aipa
18
+ aipa-cli
19
+ ```
20
+
21
+ ## Requirements
22
+
23
+ - Python 3.13+
24
+ - An OpenAI-compatible API key (`OPENAI_API_KEY`) — only needed for AI analysis, not for data fetching
25
+ - Optional: set `OPENAI_BASE_URL` for custom providers like OpenRouter
26
+
27
+ ## Quick Start
28
+
29
+ ```bash
30
+ # Launch the TUI — first run auto-starts interactive setup
31
+ aipa
32
+
33
+ # Or run setup manually at any time
34
+ aipa setup
35
+
36
+ # AI analysis with default question template
37
+ aipa analyze VCB
38
+
39
+ # AI analysis with a custom question
40
+ aipa analyze VCB --question "What is the support level and stop loss?"
41
+
42
+ # Browse available question templates
43
+ aipa analyze VCB --questions
44
+
45
+ # Use a specific question template by index
46
+ aipa analyze VCB 2 --question "What is the current trend of VCB?"
47
+
48
+ # Dump raw context data without calling the LLM (no API key needed)
49
+ aipa analyze VCB --context-only
50
+
51
+ # Override language to English (default is your saved setting)
52
+ aipa analyze VCB --lang en
53
+
54
+ # Use hourly interval with SMA instead of EMA
55
+ aipa analyze BTCUSDT --interval 1h --ma-type sma
56
+
57
+ # Analyze multiple tickers at once
58
+ aipa analyze VCB FPT VIC --interval 1D
59
+
60
+ # Run multi-agent deep research pipeline
61
+ aipa deep-research
62
+
63
+ # Deep research with a custom question and save report to file
64
+ aipa deep-research "Which sectors are leading the market?" --output report.md
65
+
66
+ # Resume a previous deep-research session from checkpoint
67
+ aipa deep-research --resume <session-id>
68
+
69
+ # Fetch raw OHLCV data as a table
70
+ aipa get-ohlcv-data VCB --interval 1D --limit 10
71
+
72
+ # Fetch with date range and no moving averages
73
+ aipa get-ohlcv-data VCB --start-date 2026-04-01 --end-date 2026-04-30 --no-ma
74
+ ```
75
+
76
+ ## CLI Commands
77
+
78
+ ### `aipa analyze`
79
+
80
+ AI-powered analysis for one or more tickers. Builds context from OHLCV data and sends it to the LLM with a question.
81
+
82
+ ```
83
+ # Default: uses question template 0 with your saved language setting
84
+ aipa analyze VCB
85
+
86
+ # Custom question
87
+ aipa analyze VCB --question "Is this a good time to buy?"
88
+
89
+ # List all question templates (trading opportunity, news, Wyckoff, etc.)
90
+ aipa analyze VCB --questions
91
+
92
+ # Raw data dump only (no LLM call, no API key required)
93
+ aipa analyze VCB --context-only
94
+
95
+ # Multi-ticker analysis
96
+ aipa analyze VCB FPT MBB
97
+
98
+ # Hourly data with SMA indicators
99
+ aipa analyze VCB --interval 1h --ma-type sma --limit 50
100
+
101
+ # Force English output
102
+ aipa analyze VCB --lang en
103
+ ```
104
+
105
+ | Flag | Description |
106
+ |---|---|
107
+ | `--question TEXT` | Custom analysis question |
108
+ | `--questions` | List available question templates and exit |
109
+ | `--context-only` | Dump raw context without LLM (no API key needed) |
110
+ | `--interval` | Time interval: `1m`, `5m`, `15m`, `30m`, `1h`, `4h`, `1D`, `1W` (default: `1D`) |
111
+ | `--limit N` | Number of bars (default: 20) |
112
+ | `--source` | Filter by source: `vn` or `crypto` |
113
+ | `--start-date` / `--end-date` | Date range (e.g. `2026-04-01`) |
114
+ | `--reference-ticker` | Reference ticker for market context (default: `VNINDEX`) |
115
+ | `--lang` | Language: `en` or `vn` (default: saved setting) |
116
+ | `--ma-type` | Moving average type: `ema` or `sma` (default: `ema`) |
117
+
118
+ ### `aipa deep-research`
119
+
120
+ Multi-agent deep research pipeline: supervisor decomposes into sector subtasks, parallel workers fetch data and analyze, aggregator synthesizes, and reviewer validates data integrity.
121
+
122
+ ```
123
+ # Default: comprehensive market overview with all VN sectors
124
+ aipa deep-research
125
+
126
+ # Custom research question
127
+ aipa deep-research "Compare banking vs real estate sectors"
128
+
129
+ # Save final report to file
130
+ aipa deep-research --output ~/reports/market-analysis.md
131
+
132
+ # Resume from a previous checkpoint session
133
+ aipa deep-research --resume 019e0cbb-0466-fa9f-d68c-2da40d35a68f
134
+
135
+ # Force Vietnamese output
136
+ aipa deep-research --lang vn
137
+ ```
138
+
139
+ | Flag | Description |
140
+ |---|---|
141
+ | `--resume ID` | Resume from a checkpoint session ID |
142
+ | `--output FILE` | Save final report to file |
143
+ | `--lang` | Language: `en` or `vn` (default: saved setting) |
144
+
145
+ ### `aipa get-ohlcv-data`
146
+
147
+ Fetch raw OHLCV data as a table (no LLM involved, works without setup).
148
+
149
+ ```
150
+ # Default: daily data with EMA indicators
151
+ aipa get-ohlcv-data VCB
152
+
153
+ # Hourly data, last 10 bars
154
+ aipa get-ohlcv-data VCB --interval 1h --limit 10
155
+
156
+ # Date range, no moving averages
157
+ aipa get-ohlcv-data VCB --start-date 2026-04-01 --end-date 2026-04-30 --no-ma
158
+
159
+ # Crypto data
160
+ aipa get-ohlcv-data BTCUSDT --interval 1D --limit 30
161
+ ```
162
+
163
+ | Flag | Description |
164
+ |---|---|
165
+ | `--interval` | Time interval (default: `1D`) |
166
+ | `--limit N` | Number of bars |
167
+ | `--start-date` / `--end-date` | Date range |
168
+ | `--source` | Filter by source: `vn` or `crypto` |
169
+ | `--ma` / `--no-ma` | Include/exclude moving averages (default: included) |
170
+ | `--ema` | Use EMA instead of SMA |
171
+
172
+ ### `aipa setup`
173
+
174
+ Interactive first-run configuration. Prompts for language, reference ticker, API key, base URL, and model. Settings are saved to `~/.aipriceaction/settings.json`. Re-running shows current values as defaults.
175
+
176
+ ```
177
+ # Run interactively
178
+ aipa setup
179
+ ```
180
+
181
+ ## First-Run Setup
182
+
183
+ Commands that require an API key will auto-run `aipa setup` on first use if not yet configured. Commands that don't need an API key always work immediately.
184
+
185
+ | Command | Setup required? |
186
+ |---|---|
187
+ | `aipa get-ohlcv-data` | No setup needed |
188
+ | `aipa analyze VCB --context-only` | No setup needed |
189
+ | `aipa analyze VCB --questions` | No setup needed |
190
+ | `aipa setup` | Runs setup |
191
+ | `aipa` | Auto-runs setup first |
192
+ | `aipa analyze VCB` | Auto-runs setup first |
193
+ | `aipa deep-research` | Auto-runs setup first |
194
+
195
+ ## TUI
196
+
197
+ Launch the TUI with `aipa`. The interface has three tabs:
198
+
199
+ - **Chat** — AI-powered chat with streaming responses, thinking/reasoning display, slash commands, and arrow-key history navigation
200
+ - **Workflows** — Structured analysis forms with question bank dropdown for ticker analysis and deep research
201
+ - **Tickers** — Browse and search available tickers
202
+
203
+ ### Slash Commands (Chat tab)
204
+
205
+ ```
206
+ /analyze VCB # Default AI analysis
207
+ /analyze VCB 1h # AI analysis with hourly interval
208
+ /analyze VCB 2 # Use question template index 2
209
+ /analyze VCB --question What is support? # Custom question
210
+ /export VCB FPT # Export context to markdown file
211
+ /deep-research # Multi-agent research
212
+ /clear # Clear chat history
213
+ /exit # Quit
214
+ ```
215
+
216
+ Press `Ctrl+O` in the Chat tab to view thinking/reasoning history.
217
+
218
+ ### Settings Tab
219
+
220
+ Configure your API key, model, and base URL directly in the TUI. Settings are saved to `~/.aipriceaction/settings.json` and shared across both TUI and CLI.
221
+
222
+ ## Configuration
223
+
224
+ Settings are loaded from `~/.aipriceaction/settings.json`. You can configure them via the TUI Settings tab or set environment variables:
225
+
226
+ | Variable | Description | Default |
227
+ |---|---|---|
228
+ | `OPENAI_API_KEY` | API key for the LLM provider | — |
229
+ | `OPENAI_BASE_URL` | Base URL for OpenAI-compatible API | OpenRouter |
230
+ | `OPENAI_MODEL` | Model name | `openrouter/owl-alpha` |
231
+ | `DATABASE_URL` | Backend API URL | `http://localhost:3000` |
232
+
233
+ ## License
234
+
235
+ MIT
@@ -1,4 +1,4 @@
1
1
  """AIPriceAction Terminal - TUI chat interface for ticker analysis."""
2
2
 
3
- __version__ = "0.1.4"
3
+ __version__ = "0.1.6"
4
4
 
@@ -38,12 +38,12 @@ class AIPriceActionApp(AppActions, App):
38
38
  self.ticker = saved["ticker"]
39
39
  self.interval = saved["interval"]
40
40
  self.language = saved["language"]
41
+ self.agent = None
42
+ self._agent_lang: str | None = None
41
43
  from aipriceaction import AIContextBuilder
42
44
  from aipriceaction import AIPriceAction as AAPClient
43
45
  self.builder = AIContextBuilder(lang=self.language)
44
46
  self.client = AAPClient()
45
- from .agents import AgentSession, AgentConfig
46
- self.agent = AgentSession(AgentConfig(lang=self.language))
47
47
  self._load_ticker_options()
48
48
  # Populate SettingsTab widgets with loaded values
49
49
  self.query_one("#setting-ticker", Input).value = self.ticker
@@ -69,6 +69,19 @@ class AIPriceActionApp(AppActions, App):
69
69
  except Exception as e:
70
70
  self.notify(f"Failed to load tickers: {e}", severity="error")
71
71
 
72
+ def _ensure_agent(self) -> bool:
73
+ """Lazy-create AgentSession on first use. Returns False if API key is missing."""
74
+ if self.agent is not None and self._agent_lang == self.language:
75
+ return True
76
+ from aipriceaction.settings import settings
77
+ if not settings.openai_api_key:
78
+ self.agent = None
79
+ return False
80
+ from .agents import AgentSession, AgentConfig
81
+ self.agent = AgentSession(AgentConfig(lang=self.language))
82
+ self._agent_lang = self.language
83
+ return True
84
+
72
85
  def compose(self) -> ComposeResult:
73
86
  yield Header(show_clock=True)
74
87
  with TabbedContent(initial="chat"):
@@ -216,7 +216,8 @@ class ChatTab(Vertical):
216
216
  )
217
217
  elif cmd == "/clear":
218
218
  log.clear()
219
- self.app.agent.clear_history()
219
+ if self.app.agent is not None:
220
+ self.app.agent.clear_history()
220
221
  elif cmd == "/exit":
221
222
  self.app.exit()
222
223
  elif cmd == "/analyze":
@@ -322,6 +323,13 @@ class ChatTab(Vertical):
322
323
  """Build context and stream AI analysis for a ticker."""
323
324
  log = self.query_one("#chat-log", RichLog)
324
325
  try:
326
+ if not self.app._ensure_agent():
327
+ log.write(
328
+ "[bold yellow]API key not configured.[/bold yellow]\n"
329
+ "Set it in the Settings tab or run [bold]aipa setup[/bold]."
330
+ )
331
+ return
332
+
325
333
  builder = self.app.builder
326
334
 
327
335
  # Build context without system prompt (agent has it already)
@@ -389,6 +397,12 @@ class ChatTab(Vertical):
389
397
  async def _run_agent_chat(self, message: str) -> None:
390
398
  """Stream an agent response into the chat log."""
391
399
  log = self.query_one("#chat-log", RichLog)
400
+ if not self.app._ensure_agent():
401
+ log.write(
402
+ "[bold yellow]API key not configured.[/bold yellow]\n"
403
+ "Set it in the Settings tab or run [bold]aipa setup[/bold]."
404
+ )
405
+ return
392
406
  try:
393
407
  await stream_agent_to_log(
394
408
  log,
@@ -3,6 +3,14 @@
3
3
  import argparse
4
4
 
5
5
 
6
+ def _ensure_setup() -> None:
7
+ """Run interactive setup if setup_done is not set."""
8
+ from .user_settings import load_settings
9
+ if not load_settings().get("setup_done"):
10
+ from .cli_setup import cmd_setup
11
+ cmd_setup()
12
+
13
+
6
14
  def run():
7
15
  parser = argparse.ArgumentParser(prog="aipa", description="AIPriceAction terminal")
8
16
  sub = parser.add_subparsers(dest="command")
@@ -44,15 +52,24 @@ def run():
44
52
  p_deep.add_argument("--output", default=None, help="Save final report to file")
45
53
  p_deep.add_argument("--lang", default=None, choices=["en", "vn"], help="Override language")
46
54
 
55
+ # aipa setup
56
+ sub.add_parser("setup", help="Interactive first-run setup")
57
+
47
58
  args = parser.parse_args()
48
59
 
49
- if args.command == "analyze":
60
+ if args.command == "setup":
61
+ from .cli_setup import cmd_setup
62
+ cmd_setup()
63
+ elif args.command == "analyze":
64
+ if not getattr(args, "context_only", False) and not getattr(args, "questions", False):
65
+ _ensure_setup()
50
66
  from .cli_commands import cmd_analyze
51
67
  cmd_analyze(args)
52
68
  elif args.command == "get-ohlcv-data":
53
69
  from .cli_commands import cmd_get_ohlcv
54
70
  cmd_get_ohlcv(args)
55
71
  elif args.command == "deep-research":
72
+ _ensure_setup()
56
73
  from .cli_commands import cmd_deep_research
57
74
  cmd_deep_research(
58
75
  question=" ".join(args.question) if args.question else "",
@@ -61,5 +78,6 @@ def run():
61
78
  lang=args.lang,
62
79
  )
63
80
  else:
81
+ _ensure_setup()
64
82
  from .app import main
65
83
  main()
@@ -0,0 +1,71 @@
1
+ """Interactive first-run setup for aipa CLI (plain terminal, no TUI)."""
2
+
3
+ from .user_settings import load_settings, save_settings
4
+
5
+
6
+ _DEFAULT_BASE_URL = "https://openrouter.ai/api/v1"
7
+ _DEFAULT_MODEL = "openai/gpt-oss-120b:free"
8
+
9
+
10
+ def cmd_setup() -> None:
11
+ """Run interactive setup and save settings."""
12
+ current = load_settings()
13
+
14
+ print("AIPriceAction Terminal Setup")
15
+ print("=" * 30)
16
+
17
+ # Language
18
+ lang = _prompt(
19
+ "Language (en/vn)",
20
+ current.get("language", "en"),
21
+ )
22
+ if lang not in ("en", "vn"):
23
+ print("Invalid language, defaulting to 'en'.")
24
+ lang = "en"
25
+
26
+ # Reference ticker
27
+ ticker = _prompt(
28
+ "Reference ticker",
29
+ current.get("ticker", "VNINDEX"),
30
+ )
31
+
32
+ # API key (optional)
33
+ api_key = _prompt(
34
+ "API key (press Enter to skip)",
35
+ current.get("api_key", ""),
36
+ )
37
+
38
+ # Base URL
39
+ base_url = _prompt(
40
+ "Base URL",
41
+ current.get("openai_base_url") or _DEFAULT_BASE_URL,
42
+ )
43
+
44
+ # Model
45
+ model = _prompt(
46
+ "Model",
47
+ current.get("openai_model") or _DEFAULT_MODEL,
48
+ )
49
+
50
+ data = {
51
+ "ticker": ticker.upper(),
52
+ "interval": current.get("interval", "1D"),
53
+ "language": lang,
54
+ "api_key": api_key,
55
+ "openai_base_url": base_url,
56
+ "openai_model": model,
57
+ "setup_done": True,
58
+ }
59
+
60
+ save_settings(data)
61
+ print("Setup complete.")
62
+
63
+
64
+ def _prompt(label: str, default: str) -> str:
65
+ """Prompt user with current default shown in brackets."""
66
+ hint = f" [{default}]" if default else ""
67
+ try:
68
+ value = input(f"{label}{hint}: ").strip()
69
+ except EOFError:
70
+ return default
71
+ return value if value else default
@@ -151,8 +151,13 @@ class SettingsTab(Vertical):
151
151
  self.app.language = language
152
152
  from aipriceaction import AIContextBuilder
153
153
  self.app.builder = AIContextBuilder(lang=language)
154
- from .agents import AgentSession, AgentConfig
155
- self.app.agent = AgentSession(AgentConfig(lang=language))
154
+ try:
155
+ from .agents import AgentSession, AgentConfig
156
+ self.app.agent = AgentSession(AgentConfig(lang=language))
157
+ self.app._agent_lang = language
158
+ except Exception:
159
+ self.app.agent = None
160
+ self.app._agent_lang = None
156
161
 
157
162
  data: dict = {
158
163
  "ticker": ticker,
@@ -13,6 +13,7 @@ _DEFAULTS = {
13
13
  "api_key": "",
14
14
  "openai_base_url": "",
15
15
  "openai_model": "",
16
+ "setup_done": False,
16
17
  }
17
18
 
18
19
 
aipa_cli-0.1.4/PKG-INFO DELETED
@@ -1,73 +0,0 @@
1
- Metadata-Version: 2.4
2
- Name: aipa-cli
3
- Version: 0.1.4
4
- Summary: Terminal TUI for AI-powered ticker analysis
5
- Project-URL: Homepage, https://github.com/quanhua92/aipriceaction
6
- Project-URL: Repository, https://github.com/quanhua92/aipriceaction
7
- Author-email: Quan Hua <quanhua92@gmail.com>
8
- License-Expression: MIT
9
- License-File: LICENSE
10
- Classifier: Development Status :: 3 - Alpha
11
- Classifier: Environment :: Console :: Curses
12
- Classifier: Intended Audience :: Financial and Insurance Industry
13
- Classifier: License :: OSI Approved :: MIT License
14
- Classifier: Programming Language :: Python :: 3
15
- Classifier: Programming Language :: Python :: 3.13
16
- Classifier: Topic :: Office/Business :: Financial
17
- Requires-Python: >=3.13
18
- Requires-Dist: aipriceaction>=0.1.9
19
- Requires-Dist: langchain-core
20
- Requires-Dist: langchain-openai
21
- Requires-Dist: langgraph
22
- Requires-Dist: textual-autocomplete>=4.0.6
23
- Requires-Dist: textual>=3.0.0
24
- Description-Content-Type: text/markdown
25
-
26
- # AIPA Terminal
27
-
28
- **Live site:** [aipriceaction.com](https://aipriceaction.com) | **GitHub:** [aipriceaction](https://github.com/quanhua92/aipriceaction) | **Frontend:** [aipriceaction-web](https://github.com/quanhua92/aipriceaction-web) | **Docker image:** [`quanhua92/aipriceaction:latest`](https://hub.docker.com/r/quanhua92/aipriceaction) | **Python SDK:** [`aipriceaction` on PyPI](https://pypi.org/project/aipriceaction/) | **AIPA Terminal:** [`aipa-cli` on PyPI](https://pypi.org/project/aipa-cli/)
29
-
30
- Textual-based terminal interface for AI-powered ticker analysis. Features streaming chat with thinking/reasoning display, autocomplete, slash commands, and workflow tabs.
31
-
32
- ## Install
33
-
34
- ```bash
35
- # Run directly (no install)
36
- uvx aipa-cli
37
-
38
- # Or install as a standalone tool
39
- uv tool install aipa-cli
40
-
41
- # Use either command
42
- aipa
43
- aipa-cli
44
- ```
45
-
46
- ## Requirements
47
-
48
- - Python 3.13+
49
- - An OpenAI-compatible API key (`OPENAI_API_KEY`)
50
- - Optional: set `OPENAI_BASE_URL` for custom providers like OpenRouter
51
-
52
- ## Usage
53
-
54
- ```
55
- aipa # Launch the TUI
56
- aipa analyze # Run ticker analysis from CLI
57
- aipa get-ohlcv-data # Fetch OHLCV data from CLI
58
- aipa deep-research # Run deep research from CLI
59
- ```
60
-
61
- ### TUI
62
-
63
- The interface has three tabs:
64
-
65
- - **Chat** — AI-powered chat with streaming responses, thinking/reasoning display, slash commands (`/analyze`, `/export`, `/clear`, `/exit`), and arrow-key history navigation
66
- - **Workflows** — Structured analysis forms for ticker analysis and deep research
67
- - **Tickers** — Browse and search available tickers
68
-
69
- Press `Ctrl+O` in the Chat tab to view thinking/reasoning history.
70
-
71
- ## License
72
-
73
- MIT
aipa_cli-0.1.4/README.md DELETED
@@ -1,48 +0,0 @@
1
- # AIPA Terminal
2
-
3
- **Live site:** [aipriceaction.com](https://aipriceaction.com) | **GitHub:** [aipriceaction](https://github.com/quanhua92/aipriceaction) | **Frontend:** [aipriceaction-web](https://github.com/quanhua92/aipriceaction-web) | **Docker image:** [`quanhua92/aipriceaction:latest`](https://hub.docker.com/r/quanhua92/aipriceaction) | **Python SDK:** [`aipriceaction` on PyPI](https://pypi.org/project/aipriceaction/) | **AIPA Terminal:** [`aipa-cli` on PyPI](https://pypi.org/project/aipa-cli/)
4
-
5
- Textual-based terminal interface for AI-powered ticker analysis. Features streaming chat with thinking/reasoning display, autocomplete, slash commands, and workflow tabs.
6
-
7
- ## Install
8
-
9
- ```bash
10
- # Run directly (no install)
11
- uvx aipa-cli
12
-
13
- # Or install as a standalone tool
14
- uv tool install aipa-cli
15
-
16
- # Use either command
17
- aipa
18
- aipa-cli
19
- ```
20
-
21
- ## Requirements
22
-
23
- - Python 3.13+
24
- - An OpenAI-compatible API key (`OPENAI_API_KEY`)
25
- - Optional: set `OPENAI_BASE_URL` for custom providers like OpenRouter
26
-
27
- ## Usage
28
-
29
- ```
30
- aipa # Launch the TUI
31
- aipa analyze # Run ticker analysis from CLI
32
- aipa get-ohlcv-data # Fetch OHLCV data from CLI
33
- aipa deep-research # Run deep research from CLI
34
- ```
35
-
36
- ### TUI
37
-
38
- The interface has three tabs:
39
-
40
- - **Chat** — AI-powered chat with streaming responses, thinking/reasoning display, slash commands (`/analyze`, `/export`, `/clear`, `/exit`), and arrow-key history navigation
41
- - **Workflows** — Structured analysis forms for ticker analysis and deep research
42
- - **Tickers** — Browse and search available tickers
43
-
44
- Press `Ctrl+O` in the Chat tab to view thinking/reasoning history.
45
-
46
- ## License
47
-
48
- MIT
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes