sqa 0.0.32 → 0.0.37

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 (109) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +92 -1
  3. data/README.md +4 -0
  4. data/Rakefile +52 -10
  5. data/docs/IMPROVEMENT_PLAN.md +531 -0
  6. data/docs/advanced/index.md +1 -13
  7. data/docs/api/index.md +547 -61
  8. data/docs/api-reference/alphavantageapi.md +1057 -0
  9. data/docs/api-reference/apierror.md +31 -0
  10. data/docs/api-reference/index.md +221 -0
  11. data/docs/api-reference/notimplemented.md +27 -0
  12. data/docs/api-reference/sqa.md +267 -0
  13. data/docs/api-reference/sqa_backtest.md +137 -0
  14. data/docs/api-reference/sqa_backtest_results.md +530 -0
  15. data/docs/api-reference/sqa_badparametererror.md +13 -0
  16. data/docs/api-reference/sqa_config.md +538 -0
  17. data/docs/api-reference/sqa_configurationerror.md +13 -0
  18. data/docs/api-reference/sqa_datafetcherror.md +56 -0
  19. data/docs/api-reference/sqa_dataframe.md +752 -0
  20. data/docs/api-reference/sqa_dataframe_alphavantage.md +30 -0
  21. data/docs/api-reference/sqa_dataframe_data.md +325 -0
  22. data/docs/api-reference/sqa_dataframe_yahoofinance.md +25 -0
  23. data/docs/api-reference/sqa_ensemble.md +413 -0
  24. data/docs/api-reference/sqa_fpop.md +211 -0
  25. data/docs/api-reference/sqa_geneticprogram.md +325 -0
  26. data/docs/api-reference/sqa_geneticprogram_individual.md +114 -0
  27. data/docs/api-reference/sqa_marketregime.md +212 -0
  28. data/docs/api-reference/sqa_multitimeframe.md +227 -0
  29. data/docs/api-reference/sqa_patternmatcher.md +195 -0
  30. data/docs/api-reference/sqa_pluginmanager.md +55 -0
  31. data/docs/api-reference/sqa_portfolio.md +455 -0
  32. data/docs/api-reference/sqa_portfolio_position.md +220 -0
  33. data/docs/api-reference/sqa_portfolio_trade.md +332 -0
  34. data/docs/api-reference/sqa_portfoliooptimizer.md +248 -0
  35. data/docs/api-reference/sqa_riskmanager.md +388 -0
  36. data/docs/api-reference/sqa_seasonalanalyzer.md +121 -0
  37. data/docs/api-reference/sqa_sectoranalyzer.md +163 -0
  38. data/docs/api-reference/sqa_stock.md +649 -0
  39. data/docs/api-reference/sqa_strategy.md +178 -0
  40. data/docs/api-reference/sqa_strategy_bollingerbands.md +26 -0
  41. data/docs/api-reference/sqa_strategy_common.md +29 -0
  42. data/docs/api-reference/sqa_strategy_consensus.md +129 -0
  43. data/docs/api-reference/sqa_strategy_ema.md +41 -0
  44. data/docs/api-reference/sqa_strategy_kbs.md +154 -0
  45. data/docs/api-reference/sqa_strategy_macd.md +26 -0
  46. data/docs/api-reference/sqa_strategy_mp.md +41 -0
  47. data/docs/api-reference/sqa_strategy_mr.md +41 -0
  48. data/docs/api-reference/sqa_strategy_random.md +41 -0
  49. data/docs/api-reference/sqa_strategy_rsi.md +41 -0
  50. data/docs/api-reference/sqa_strategy_sma.md +41 -0
  51. data/docs/api-reference/sqa_strategy_stochastic.md +26 -0
  52. data/docs/api-reference/sqa_strategy_volumebreakout.md +26 -0
  53. data/docs/api-reference/sqa_strategygenerator.md +298 -0
  54. data/docs/api-reference/sqa_strategygenerator_pattern.md +264 -0
  55. data/docs/api-reference/sqa_strategygenerator_patterncontext.md +326 -0
  56. data/docs/api-reference/sqa_strategygenerator_profitablepoint.md +424 -0
  57. data/docs/api-reference/sqa_stream.md +256 -0
  58. data/docs/api-reference/sqa_ticker.md +175 -0
  59. data/docs/api-reference/string.md +135 -0
  60. data/docs/assets/images/advanced-workflow.svg +89 -0
  61. data/docs/assets/images/architecture.svg +107 -0
  62. data/docs/assets/images/data-flow.svg +138 -0
  63. data/docs/assets/images/getting-started-workflow.svg +88 -0
  64. data/docs/assets/images/strategy-flow.svg +78 -0
  65. data/docs/assets/images/system-architecture.svg +150 -0
  66. data/docs/concepts/index.md +292 -19
  67. data/docs/getting-started/index.md +1 -14
  68. data/docs/index.md +26 -23
  69. data/docs/llms.txt +109 -0
  70. data/docs/strategies/kbs.md +15 -14
  71. data/docs/strategy.md +381 -3
  72. data/docs/terms_of_use.md +1 -1
  73. data/examples/README.md +10 -0
  74. data/lib/api/alpha_vantage_api.rb +3 -7
  75. data/lib/sqa/config.rb +109 -28
  76. data/lib/sqa/data_frame/data.rb +13 -1
  77. data/lib/sqa/data_frame.rb +168 -26
  78. data/lib/sqa/errors.rb +79 -17
  79. data/lib/sqa/init.rb +70 -15
  80. data/lib/sqa/pattern_matcher.rb +4 -4
  81. data/lib/sqa/portfolio.rb +1 -1
  82. data/lib/sqa/sector_analyzer.rb +3 -11
  83. data/lib/sqa/stock.rb +169 -15
  84. data/lib/sqa/strategy.rb +62 -4
  85. data/lib/sqa/ticker.rb +106 -48
  86. data/lib/sqa/version.rb +1 -1
  87. data/lib/sqa.rb +4 -4
  88. data/mkdocs.yml +68 -81
  89. metadata +89 -21
  90. data/docs/README.md +0 -43
  91. data/examples/sinatra_app/Gemfile +0 -42
  92. data/examples/sinatra_app/Gemfile.lock +0 -268
  93. data/examples/sinatra_app/QUICKSTART.md +0 -169
  94. data/examples/sinatra_app/README.md +0 -471
  95. data/examples/sinatra_app/RUNNING_WITHOUT_TALIB.md +0 -90
  96. data/examples/sinatra_app/TROUBLESHOOTING.md +0 -95
  97. data/examples/sinatra_app/app.rb +0 -404
  98. data/examples/sinatra_app/config.ru +0 -5
  99. data/examples/sinatra_app/public/css/style.css +0 -723
  100. data/examples/sinatra_app/public/debug_macd.html +0 -82
  101. data/examples/sinatra_app/public/js/app.js +0 -107
  102. data/examples/sinatra_app/start.sh +0 -53
  103. data/examples/sinatra_app/views/analyze.erb +0 -306
  104. data/examples/sinatra_app/views/backtest.erb +0 -325
  105. data/examples/sinatra_app/views/dashboard.erb +0 -831
  106. data/examples/sinatra_app/views/error.erb +0 -58
  107. data/examples/sinatra_app/views/index.erb +0 -118
  108. data/examples/sinatra_app/views/layout.erb +0 -61
  109. data/examples/sinatra_app/views/portfolio.erb +0 -43
@@ -0,0 +1,325 @@
1
+ # 📦 SQA::GeneticProgram
2
+
3
+ !!! abstract "Source Information"
4
+ **Defined in:** `lib/sqa/gp.rb:35`
5
+
6
+ **Inherits from:** `Object`
7
+
8
+ ## 🔨 Instance Methods
9
+
10
+ ### `#stock()`
11
+
12
+ Returns the value of attribute stock.
13
+
14
+
15
+
16
+
17
+ ??? info "Source Location"
18
+ `lib/sqa/gp.rb:54`
19
+
20
+ ---
21
+
22
+ ### `#population()`
23
+
24
+ Returns the value of attribute population.
25
+
26
+
27
+
28
+
29
+ ??? info "Source Location"
30
+ `lib/sqa/gp.rb:54`
31
+
32
+ ---
33
+
34
+ ### `#best_individual()`
35
+
36
+ Returns the value of attribute best_individual.
37
+
38
+
39
+
40
+
41
+ ??? info "Source Location"
42
+ `lib/sqa/gp.rb:54`
43
+
44
+ ---
45
+
46
+ ### `#generation()`
47
+
48
+ Returns the value of attribute generation.
49
+
50
+
51
+
52
+
53
+ ??? info "Source Location"
54
+ `lib/sqa/gp.rb:54`
55
+
56
+ ---
57
+
58
+ ### `#history()`
59
+
60
+ Returns the value of attribute history.
61
+
62
+
63
+
64
+
65
+ ??? info "Source Location"
66
+ `lib/sqa/gp.rb:54`
67
+
68
+ ---
69
+
70
+ ### `#population_size()`
71
+
72
+ Returns the value of attribute population_size.
73
+
74
+
75
+
76
+
77
+ ??? info "Source Location"
78
+ `lib/sqa/gp.rb:55`
79
+
80
+ ---
81
+
82
+ ### `#population_size=(value)`
83
+
84
+ Sets the attribute population_size
85
+
86
+ !!! info "Parameters"
87
+
88
+ | Name | Type | Description |
89
+ |------|------|-------------|
90
+ | `value` | `Any` | the value to set the attribute population_size to. |
91
+
92
+
93
+ ??? info "Source Location"
94
+ `lib/sqa/gp.rb:55`
95
+
96
+ ---
97
+
98
+ ### `#generations()`
99
+
100
+ Returns the value of attribute generations.
101
+
102
+
103
+
104
+
105
+ ??? info "Source Location"
106
+ `lib/sqa/gp.rb:55`
107
+
108
+ ---
109
+
110
+ ### `#generations=(value)`
111
+
112
+ Sets the attribute generations
113
+
114
+ !!! info "Parameters"
115
+
116
+ | Name | Type | Description |
117
+ |------|------|-------------|
118
+ | `value` | `Any` | the value to set the attribute generations to. |
119
+
120
+
121
+ ??? info "Source Location"
122
+ `lib/sqa/gp.rb:55`
123
+
124
+ ---
125
+
126
+ ### `#mutation_rate()`
127
+
128
+ Returns the value of attribute mutation_rate.
129
+
130
+
131
+
132
+
133
+ ??? info "Source Location"
134
+ `lib/sqa/gp.rb:55`
135
+
136
+ ---
137
+
138
+ ### `#mutation_rate=(value)`
139
+
140
+ Sets the attribute mutation_rate
141
+
142
+ !!! info "Parameters"
143
+
144
+ | Name | Type | Description |
145
+ |------|------|-------------|
146
+ | `value` | `Any` | the value to set the attribute mutation_rate to. |
147
+
148
+
149
+ ??? info "Source Location"
150
+ `lib/sqa/gp.rb:55`
151
+
152
+ ---
153
+
154
+ ### `#crossover_rate()`
155
+
156
+ Returns the value of attribute crossover_rate.
157
+
158
+
159
+
160
+
161
+ ??? info "Source Location"
162
+ `lib/sqa/gp.rb:55`
163
+
164
+ ---
165
+
166
+ ### `#crossover_rate=(value)`
167
+
168
+ Sets the attribute crossover_rate
169
+
170
+ !!! info "Parameters"
171
+
172
+ | Name | Type | Description |
173
+ |------|------|-------------|
174
+ | `value` | `Any` | the value to set the attribute crossover_rate to. |
175
+
176
+
177
+ ??? info "Source Location"
178
+ `lib/sqa/gp.rb:55`
179
+
180
+ ---
181
+
182
+ ### `#elitism_count()`
183
+
184
+ Returns the value of attribute elitism_count.
185
+
186
+
187
+
188
+
189
+ ??? info "Source Location"
190
+ `lib/sqa/gp.rb:55`
191
+
192
+ ---
193
+
194
+ ### `#elitism_count=(value)`
195
+
196
+ Sets the attribute elitism_count
197
+
198
+ !!! info "Parameters"
199
+
200
+ | Name | Type | Description |
201
+ |------|------|-------------|
202
+ | `value` | `Any` | the value to set the attribute elitism_count to. |
203
+
204
+
205
+ ??? info "Source Location"
206
+ `lib/sqa/gp.rb:55`
207
+
208
+ ---
209
+
210
+ ### `#initialize(stock:, population_size: = 50, generations: = 100, mutation_rate: = 0.15, crossover_rate: = 0.7, elitism_count: = 2)`
211
+
212
+
213
+ !!! success "Returns"
214
+
215
+ **Type:** `GeneticProgram`
216
+
217
+
218
+
219
+ a new instance of GeneticProgram
220
+
221
+ ??? info "Source Location"
222
+ `lib/sqa/gp.rb:57`
223
+
224
+ ---
225
+
226
+ ### `#define_genes(**constraints)`
227
+
228
+ Define the parameter space for evolution
229
+
230
+ Example:
231
+ gp.define_genes(
232
+ indicator: [:rsi, :macd, :stoch],
233
+ period: (5..30).to_a,
234
+ buy_threshold: (20..40).to_a,
235
+ sell_threshold: (60..80).to_a
236
+ )
237
+
238
+
239
+
240
+
241
+ ??? info "Source Location"
242
+ `lib/sqa/gp.rb:82`
243
+
244
+ ---
245
+
246
+ ### `#fitness(&block)`
247
+
248
+ Define how to evaluate fitness for an individual
249
+
250
+ The block receives an individual's genes hash and should return
251
+ a numeric fitness value (higher is better)
252
+
253
+ Example:
254
+ gp.fitness do |genes|
255
+ backtest = SQA::Backtest.new(
256
+ stock: stock,
257
+ strategy: create_strategy_from_genes(genes),
258
+ initial_capital: 10_000
259
+ )
260
+ results = backtest.run
261
+ results.total_return # Higher return = higher fitness
262
+ end
263
+
264
+
265
+
266
+
267
+ ??? info "Source Location"
268
+ `lib/sqa/gp.rb:102`
269
+
270
+ ---
271
+
272
+ ### `#evolve()`
273
+
274
+ Run the genetic algorithm evolution
275
+
276
+
277
+
278
+
279
+ ??? info "Source Location"
280
+ `lib/sqa/gp.rb:108`
281
+
282
+ ---
283
+
284
+ ## 📝 Attributes
285
+
286
+ ### 👁️ `stock` <small>read-only</small>
287
+
288
+ Returns the value of attribute stock.
289
+
290
+ ### 👁️ `population` <small>read-only</small>
291
+
292
+ Returns the value of attribute population.
293
+
294
+ ### 👁️ `best_individual` <small>read-only</small>
295
+
296
+ Returns the value of attribute best_individual.
297
+
298
+ ### 👁️ `generation` <small>read-only</small>
299
+
300
+ Returns the value of attribute generation.
301
+
302
+ ### 👁️ `history` <small>read-only</small>
303
+
304
+ Returns the value of attribute history.
305
+
306
+ ### 🔄 `population_size` <small>read/write</small>
307
+
308
+ Returns the value of attribute population_size.
309
+
310
+ ### 🔄 `generations` <small>read/write</small>
311
+
312
+ Returns the value of attribute generations.
313
+
314
+ ### 🔄 `mutation_rate` <small>read/write</small>
315
+
316
+ Returns the value of attribute mutation_rate.
317
+
318
+ ### 🔄 `crossover_rate` <small>read/write</small>
319
+
320
+ Returns the value of attribute crossover_rate.
321
+
322
+ ### 🔄 `elitism_count` <small>read/write</small>
323
+
324
+ Returns the value of attribute elitism_count.
325
+
@@ -0,0 +1,114 @@
1
+ # 📦 SQA::GeneticProgram::Individual
2
+
3
+ !!! note "Description"
4
+ Represents an individual trading strategy with specific parameters
5
+
6
+ !!! abstract "Source Information"
7
+ **Defined in:** `lib/sqa/gp.rb:37`
8
+
9
+ **Inherits from:** `Object`
10
+
11
+ ## 🔨 Instance Methods
12
+
13
+ ### `#genes()`
14
+
15
+ Returns the value of attribute genes.
16
+
17
+
18
+
19
+
20
+ ??? info "Source Location"
21
+ `lib/sqa/gp.rb:38`
22
+
23
+ ---
24
+
25
+ ### `#genes=(value)`
26
+
27
+ Sets the attribute genes
28
+
29
+ !!! info "Parameters"
30
+
31
+ | Name | Type | Description |
32
+ |------|------|-------------|
33
+ | `value` | `Any` | the value to set the attribute genes to. |
34
+
35
+
36
+ ??? info "Source Location"
37
+ `lib/sqa/gp.rb:38`
38
+
39
+ ---
40
+
41
+ ### `#fitness()`
42
+
43
+ Returns the value of attribute fitness.
44
+
45
+
46
+
47
+
48
+ ??? info "Source Location"
49
+ `lib/sqa/gp.rb:38`
50
+
51
+ ---
52
+
53
+ ### `#fitness=(value)`
54
+
55
+ Sets the attribute fitness
56
+
57
+ !!! info "Parameters"
58
+
59
+ | Name | Type | Description |
60
+ |------|------|-------------|
61
+ | `value` | `Any` | the value to set the attribute fitness to. |
62
+
63
+
64
+ ??? info "Source Location"
65
+ `lib/sqa/gp.rb:38`
66
+
67
+ ---
68
+
69
+ ### `#initialize(genes: = {}, fitness: = nil)`
70
+
71
+
72
+ !!! success "Returns"
73
+
74
+ **Type:** `Individual`
75
+
76
+
77
+
78
+ a new instance of Individual
79
+
80
+ ??? info "Source Location"
81
+ `lib/sqa/gp.rb:40`
82
+
83
+ ---
84
+
85
+ ### `#clone()`
86
+
87
+
88
+
89
+
90
+ ??? info "Source Location"
91
+ `lib/sqa/gp.rb:45`
92
+
93
+ ---
94
+
95
+ ### `#to_s()`
96
+
97
+
98
+
99
+
100
+ ??? info "Source Location"
101
+ `lib/sqa/gp.rb:49`
102
+
103
+ ---
104
+
105
+ ## 📝 Attributes
106
+
107
+ ### 🔄 `genes` <small>read/write</small>
108
+
109
+ Returns the value of attribute genes.
110
+
111
+ ### 🔄 `fitness` <small>read/write</small>
112
+
113
+ Returns the value of attribute fitness.
114
+
@@ -0,0 +1,212 @@
1
+ # 🔧 SQA::MarketRegime
2
+
3
+ !!! abstract "Source Information"
4
+ **Defined in:** `lib/sqa/market_regime.rb:17`
5
+
6
+ ## 🏭 Class Methods
7
+
8
+ ### `.detect(stock, lookback: = nil, window: = nil)`
9
+
10
+ Detect current market regime for a stock
11
+
12
+ !!! info "Parameters"
13
+
14
+ | Name | Type | Description |
15
+ |------|------|-------------|
16
+ | `stock` | `SQA::Stock` | Stock to analyze |
17
+ | `lookback` | `Integer` | Days to look back for regime detection |
18
+ | `window` | `Integer` | Alias for lookback (for backward compatibility) |
19
+ !!! success "Returns"
20
+
21
+ **Type:** `Hash`
22
+
23
+
24
+
25
+ Regime metadata with both symbolic and numeric values
26
+
27
+ ??? info "Source Location"
28
+ `lib/sqa/market_regime.rb:26`
29
+
30
+ ---
31
+
32
+ ### `.detect_history(stock, window: = 60)`
33
+
34
+ Detect market regimes across entire history
35
+
36
+ Splits historical data into regime periods
37
+
38
+ !!! info "Parameters"
39
+
40
+ | Name | Type | Description |
41
+ |------|------|-------------|
42
+ | `stock` | `SQA::Stock` | Stock to analyze |
43
+ | `window` | `Integer` | Rolling window for regime detection |
44
+ !!! success "Returns"
45
+
46
+ **Type:** `Array<Hash>`
47
+
48
+
49
+
50
+ Array of regime periods
51
+
52
+ ??? info "Source Location"
53
+ `lib/sqa/market_regime.rb:61`
54
+
55
+ ---
56
+
57
+ ### `.detect_trend_with_score(prices)`
58
+
59
+ Classify regime type based on trend with numeric score
60
+
61
+ !!! info "Parameters"
62
+
63
+ | Name | Type | Description |
64
+ |------|------|-------------|
65
+ | `prices` | `Array<Float>` | Price array |
66
+ !!! success "Returns"
67
+
68
+ **Type:** `Hash`
69
+
70
+
71
+
72
+ { type: Symbol, score: Float }
73
+
74
+ ??? info "Source Location"
75
+ `lib/sqa/market_regime.rb:109`
76
+
77
+ ---
78
+
79
+ ### `.detect_trend(prices)`
80
+
81
+ Classify regime type based on trend (backward compatibility)
82
+
83
+ !!! info "Parameters"
84
+
85
+ | Name | Type | Description |
86
+ |------|------|-------------|
87
+ | `prices` | `Array<Float>` | Price array |
88
+ !!! success "Returns"
89
+
90
+ **Type:** `Symbol`
91
+
92
+
93
+
94
+ :bull, :bear, or :sideways
95
+
96
+ ??? info "Source Location"
97
+ `lib/sqa/market_regime.rb:136`
98
+
99
+ ---
100
+
101
+ ### `.detect_volatility_with_score(prices)`
102
+
103
+ Detect volatility regime with numeric score
104
+
105
+ !!! info "Parameters"
106
+
107
+ | Name | Type | Description |
108
+ |------|------|-------------|
109
+ | `prices` | `Array<Float>` | Price array |
110
+ !!! success "Returns"
111
+
112
+ **Type:** `Hash`
113
+
114
+
115
+
116
+ { type: Symbol, score: Float }
117
+
118
+ ??? info "Source Location"
119
+ `lib/sqa/market_regime.rb:145`
120
+
121
+ ---
122
+
123
+ ### `.detect_volatility(prices)`
124
+
125
+ Detect volatility regime (backward compatibility)
126
+
127
+ !!! info "Parameters"
128
+
129
+ | Name | Type | Description |
130
+ |------|------|-------------|
131
+ | `prices` | `Array<Float>` | Price array |
132
+ !!! success "Returns"
133
+
134
+ **Type:** `Symbol`
135
+
136
+
137
+
138
+ :low, :medium, or :high
139
+
140
+ ??? info "Source Location"
141
+ `lib/sqa/market_regime.rb:170`
142
+
143
+ ---
144
+
145
+ ### `.detect_strength_with_score(prices)`
146
+
147
+ Detect trend strength with numeric score
148
+
149
+ !!! info "Parameters"
150
+
151
+ | Name | Type | Description |
152
+ |------|------|-------------|
153
+ | `prices` | `Array<Float>` | Price array |
154
+ !!! success "Returns"
155
+
156
+ **Type:** `Hash`
157
+
158
+
159
+
160
+ { type: Symbol, score: Float }
161
+
162
+ ??? info "Source Location"
163
+ `lib/sqa/market_regime.rb:179`
164
+
165
+ ---
166
+
167
+ ### `.detect_strength(prices)`
168
+
169
+ Detect trend strength (backward compatibility)
170
+
171
+ !!! info "Parameters"
172
+
173
+ | Name | Type | Description |
174
+ |------|------|-------------|
175
+ | `prices` | `Array<Float>` | Price array |
176
+ !!! success "Returns"
177
+
178
+ **Type:** `Symbol`
179
+
180
+
181
+
182
+ :weak, :moderate, or :strong
183
+
184
+ ??? info "Source Location"
185
+ `lib/sqa/market_regime.rb:211`
186
+
187
+ ---
188
+
189
+ ### `.split_by_regime(stock)`
190
+
191
+ Split data by regime
192
+
193
+ !!! info "Parameters"
194
+
195
+ | Name | Type | Description |
196
+ |------|------|-------------|
197
+ | `stock` | `SQA::Stock` | Stock to analyze |
198
+ !!! success "Returns"
199
+
200
+ **Type:** `Hash`
201
+
202
+
203
+
204
+ Data grouped by regime type
205
+
206
+ ??? info "Source Location"
207
+ `lib/sqa/market_regime.rb:220`
208
+
209
+ ---
210
+
211
+ ## 📝 Attributes
212
+