@rune-kit/rune 2.8.0 → 2.11.0
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.
- package/LICENSE +21 -21
- package/README.md +68 -34
- package/agents/adversary.md +27 -0
- package/agents/architect.md +19 -29
- package/agents/asset-creator.md +18 -4
- package/agents/audit.md +25 -4
- package/agents/autopsy.md +19 -4
- package/agents/ba.md +35 -0
- package/agents/brainstorm.md +31 -4
- package/agents/browser-pilot.md +21 -4
- package/agents/coder.md +21 -29
- package/agents/completion-gate.md +20 -4
- package/agents/constraint-check.md +18 -4
- package/agents/context-engine.md +22 -4
- package/agents/context-pack.md +32 -0
- package/agents/cook.md +41 -4
- package/agents/db.md +19 -4
- package/agents/debug.md +33 -4
- package/agents/dependency-doctor.md +20 -4
- package/agents/deploy.md +27 -4
- package/agents/design.md +22 -4
- package/agents/doc-processor.md +27 -0
- package/agents/docs-seeker.md +19 -4
- package/agents/docs.md +31 -0
- package/agents/fix.md +37 -4
- package/agents/git.md +29 -0
- package/agents/hallucination-guard.md +20 -4
- package/agents/incident.md +21 -4
- package/agents/integrity-check.md +18 -4
- package/agents/journal.md +19 -4
- package/agents/launch.md +32 -4
- package/agents/logic-guardian.md +26 -11
- package/agents/marketing.md +23 -4
- package/agents/mcp-builder.md +26 -0
- package/agents/neural-memory.md +30 -0
- package/agents/onboard.md +22 -4
- package/agents/perf.md +21 -4
- package/agents/plan.md +29 -4
- package/agents/preflight.md +22 -4
- package/agents/problem-solver.md +20 -4
- package/agents/rescue.md +23 -4
- package/agents/research.md +19 -4
- package/agents/researcher.md +19 -29
- package/agents/retro.md +32 -0
- package/agents/review-intake.md +20 -4
- package/agents/review.md +32 -4
- package/agents/reviewer.md +20 -28
- package/agents/safeguard.md +19 -4
- package/agents/sast.md +18 -4
- package/agents/scaffold.md +41 -0
- package/agents/scanner.md +19 -28
- package/agents/scope-guard.md +18 -4
- package/agents/scout.md +23 -4
- package/agents/sentinel-env.md +26 -0
- package/agents/sentinel.md +33 -4
- package/agents/sequential-thinking.md +20 -4
- package/agents/session-bridge.md +24 -4
- package/agents/skill-forge.md +22 -4
- package/agents/skill-router.md +26 -4
- package/agents/slides.md +24 -0
- package/agents/surgeon.md +19 -4
- package/agents/team.md +30 -4
- package/agents/test.md +36 -4
- package/agents/trend-scout.md +17 -4
- package/agents/verification.md +20 -4
- package/agents/video-creator.md +20 -4
- package/agents/watchdog.md +19 -4
- package/agents/worktree.md +17 -4
- package/commands/rune.md +168 -168
- package/compiler/__tests__/analytics.test.js +370 -0
- package/compiler/adapters/openclaw.js +2 -2
- package/compiler/analytics.js +385 -0
- package/compiler/bin/rune.js +68 -2
- package/compiler/dashboard.js +883 -0
- package/compiler/transforms/branding.js +1 -1
- package/contexts/dev.md +34 -34
- package/contexts/research.md +43 -43
- package/contexts/review.md +55 -55
- package/extensions/ai-ml/PACK.md +88 -88
- package/extensions/ai-ml/skills/ai-agents.md +172 -172
- package/extensions/ai-ml/skills/code-sandbox.md +187 -187
- package/extensions/ai-ml/skills/deep-research.md +146 -146
- package/extensions/ai-ml/skills/embedding-search.md +66 -66
- package/extensions/ai-ml/skills/fine-tuning-guide.md +74 -74
- package/extensions/ai-ml/skills/llm-architect.md +125 -125
- package/extensions/ai-ml/skills/llm-integration.md +64 -64
- package/extensions/ai-ml/skills/prompt-patterns.md +72 -72
- package/extensions/ai-ml/skills/rag-patterns.md +66 -66
- package/extensions/ai-ml/skills/web-extraction.md +114 -114
- package/extensions/analytics/PACK.md +92 -92
- package/extensions/analytics/skills/ab-testing.md +72 -72
- package/extensions/analytics/skills/dashboard-patterns.md +83 -83
- package/extensions/analytics/skills/data-validation.md +68 -68
- package/extensions/analytics/skills/funnel-analysis.md +81 -81
- package/extensions/analytics/skills/sql-patterns.md +57 -57
- package/extensions/analytics/skills/statistical-analysis.md +79 -79
- package/extensions/analytics/skills/tracking-setup.md +71 -71
- package/extensions/backend/PACK.md +104 -104
- package/extensions/backend/skills/api-patterns.md +84 -84
- package/extensions/backend/skills/async-pipeline.md +193 -193
- package/extensions/backend/skills/auth-patterns.md +97 -97
- package/extensions/backend/skills/background-jobs.md +133 -133
- package/extensions/backend/skills/caching-patterns.md +108 -108
- package/extensions/backend/skills/cli-generation.md +133 -133
- package/extensions/backend/skills/database-patterns.md +87 -87
- package/extensions/backend/skills/middleware-patterns.md +104 -104
- package/extensions/chrome-ext/PACK.md +93 -93
- package/extensions/chrome-ext/skills/cws-preflight.md +143 -143
- package/extensions/chrome-ext/skills/cws-publish.md +104 -104
- package/extensions/chrome-ext/skills/ext-ai-integration.md +251 -251
- package/extensions/chrome-ext/skills/ext-messaging.md +139 -139
- package/extensions/chrome-ext/skills/ext-storage.md +133 -133
- package/extensions/chrome-ext/skills/mv3-scaffold.md +164 -164
- package/extensions/content/PACK.md +96 -96
- package/extensions/content/skills/blog-patterns.md +88 -88
- package/extensions/content/skills/cms-integration.md +131 -131
- package/extensions/content/skills/content-scoring.md +107 -107
- package/extensions/content/skills/i18n.md +83 -83
- package/extensions/content/skills/mdx-authoring.md +137 -137
- package/extensions/content/skills/reference.md +1014 -1014
- package/extensions/content/skills/seo-patterns.md +67 -67
- package/extensions/content/skills/video-repurpose.md +153 -153
- package/extensions/devops/PACK.md +101 -101
- package/extensions/devops/skills/chaos-testing.md +67 -67
- package/extensions/devops/skills/ci-cd.md +75 -75
- package/extensions/devops/skills/docker.md +58 -58
- package/extensions/devops/skills/edge-serverless.md +163 -163
- package/extensions/devops/skills/infra-as-code.md +158 -158
- package/extensions/devops/skills/kubernetes.md +110 -110
- package/extensions/devops/skills/monitoring.md +57 -57
- package/extensions/devops/skills/server-setup.md +64 -64
- package/extensions/devops/skills/ssl-domain.md +42 -42
- package/extensions/ecommerce/PACK.md +116 -116
- package/extensions/ecommerce/skills/cart-system.md +79 -79
- package/extensions/ecommerce/skills/inventory-mgmt.md +102 -102
- package/extensions/ecommerce/skills/order-management.md +126 -126
- package/extensions/ecommerce/skills/payment-integration.md +472 -472
- package/extensions/ecommerce/skills/shopify-dev.md +69 -69
- package/extensions/ecommerce/skills/subscription-billing.md +93 -93
- package/extensions/ecommerce/skills/tax-compliance.md +117 -117
- package/extensions/gamedev/PACK.md +142 -142
- package/extensions/gamedev/skills/asset-pipeline.md +74 -74
- package/extensions/gamedev/skills/audio-system.md +129 -129
- package/extensions/gamedev/skills/camera-system.md +87 -87
- package/extensions/gamedev/skills/ecs.md +98 -98
- package/extensions/gamedev/skills/game-loops.md +72 -72
- package/extensions/gamedev/skills/input-system.md +199 -199
- package/extensions/gamedev/skills/multiplayer.md +180 -180
- package/extensions/gamedev/skills/particles.md +105 -105
- package/extensions/gamedev/skills/physics-engine.md +89 -89
- package/extensions/gamedev/skills/scene-management.md +146 -146
- package/extensions/gamedev/skills/threejs-patterns.md +90 -90
- package/extensions/gamedev/skills/webgl.md +71 -71
- package/extensions/mobile/PACK.md +106 -106
- package/extensions/mobile/skills/app-store-connect.md +152 -152
- package/extensions/mobile/skills/app-store-prep.md +66 -66
- package/extensions/mobile/skills/deep-linking.md +109 -109
- package/extensions/mobile/skills/flutter.md +60 -60
- package/extensions/mobile/skills/ios-build-pipeline.md +142 -142
- package/extensions/mobile/skills/native-bridge.md +66 -66
- package/extensions/mobile/skills/ota-updates.md +97 -97
- package/extensions/mobile/skills/push-notifications.md +111 -111
- package/extensions/mobile/skills/react-native.md +82 -82
- package/extensions/saas/PACK.md +116 -116
- package/extensions/saas/skills/billing-integration.md +200 -200
- package/extensions/saas/skills/feature-flags.md +130 -130
- package/extensions/saas/skills/multi-tenant.md +103 -103
- package/extensions/saas/skills/onboarding-flow.md +139 -139
- package/extensions/saas/skills/subscription-flow.md +95 -95
- package/extensions/saas/skills/team-management.md +144 -144
- package/extensions/security/PACK.md +99 -99
- package/extensions/security/skills/api-security.md +140 -140
- package/extensions/security/skills/compliance.md +68 -68
- package/extensions/security/skills/owasp-audit.md +64 -64
- package/extensions/security/skills/pentest-patterns.md +77 -77
- package/extensions/security/skills/secret-mgmt.md +65 -65
- package/extensions/security/skills/supply-chain.md +65 -65
- package/extensions/trading/PACK.md +80 -80
- package/extensions/trading/skills/chart-components.md +55 -55
- package/extensions/trading/skills/experiment-loop.md +125 -125
- package/extensions/trading/skills/fintech-patterns.md +47 -47
- package/extensions/trading/skills/indicator-library.md +58 -58
- package/extensions/trading/skills/quant-analysis.md +111 -111
- package/extensions/trading/skills/realtime-data.md +58 -58
- package/extensions/trading/skills/trade-logic.md +104 -104
- package/extensions/ui/PACK.md +130 -130
- package/extensions/ui/skills/a11y-audit.md +91 -91
- package/extensions/ui/skills/animation-patterns.md +127 -106
- package/extensions/ui/skills/component-patterns.md +100 -75
- package/extensions/ui/skills/design-decision.md +108 -108
- package/extensions/ui/skills/design-system.md +68 -68
- package/extensions/ui/skills/landing-patterns.md +155 -155
- package/extensions/ui/skills/palette-picker.md +173 -173
- package/extensions/ui/skills/react-health.md +90 -90
- package/extensions/ui/skills/type-system.md +125 -125
- package/extensions/ui/skills/web-vitals.md +153 -153
- package/extensions/zalo/PACK.md +145 -145
- package/extensions/zalo/skills/zalo-oa-mcp.md +317 -317
- package/extensions/zalo/skills/zalo-oa-messaging.md +429 -429
- package/extensions/zalo/skills/zalo-oa-setup.md +236 -236
- package/extensions/zalo/skills/zalo-oa-webhook.md +189 -189
- package/extensions/zalo/skills/zalo-personal-messaging.md +194 -194
- package/extensions/zalo/skills/zalo-personal-setup.md +153 -153
- package/extensions/zalo/skills/zalo-rate-guard.md +219 -219
- package/hooks/auto-format/index.cjs +48 -48
- package/hooks/context-watch/index.cjs +95 -68
- package/hooks/hooks.json +111 -111
- package/hooks/metrics-collector/index.cjs +86 -42
- package/hooks/post-session-reflect/index.cjs +189 -153
- package/hooks/pre-compact/index.cjs +95 -95
- package/hooks/run-hook.cmd +1 -1
- package/hooks/secrets-scan/index.cjs +100 -100
- package/hooks/session-start/index.cjs +71 -65
- package/hooks/typecheck/index.cjs +65 -65
- package/package.json +63 -63
- package/references/ui-pro-max-data/LICENSE-UI-PRO-MAX +21 -21
- package/references/ui-pro-max-data/charts.csv +26 -26
- package/references/ui-pro-max-data/colors.csv +161 -161
- package/references/ui-pro-max-data/styles.csv +68 -68
- package/references/ui-pro-max-data/typography.csv +74 -74
- package/references/ui-pro-max-data/ui-reasoning.csv +162 -162
- package/references/ui-pro-max-data/ux-guidelines.csv +99 -99
- package/skills/adversary/SKILL.md +283 -283
- package/skills/asset-creator/SKILL.md +157 -157
- package/skills/audit/SKILL.md +148 -2
- package/skills/autopsy/SKILL.md +335 -259
- package/skills/autopsy/references/repo-analysis-patterns.md +113 -0
- package/skills/ba/SKILL.md +72 -2
- package/skills/brainstorm/SKILL.md +342 -341
- package/skills/browser-pilot/SKILL.md +168 -168
- package/skills/constraint-check/SKILL.md +165 -165
- package/skills/context-engine/SKILL.md +404 -404
- package/skills/cook/SKILL.md +917 -834
- package/skills/cook/references/output-format.md +33 -0
- package/skills/db/SKILL.md +273 -272
- package/skills/debug/SKILL.md +465 -443
- package/skills/dependency-doctor/SKILL.md +265 -235
- package/skills/deploy/SKILL.md +274 -231
- package/skills/design/DESIGN-REFERENCE.md +365 -365
- package/skills/design/SKILL.md +589 -482
- package/skills/doc-processor/SKILL.md +254 -254
- package/skills/docs/SKILL.md +374 -373
- package/skills/docs-seeker/SKILL.md +177 -177
- package/skills/fix/SKILL.md +330 -308
- package/skills/git/SKILL.md +339 -339
- package/skills/graft/SKILL.md +352 -0
- package/skills/graft/references/challenge-framework.md +98 -0
- package/skills/graft/references/mode-decision.md +44 -0
- package/skills/hallucination-guard/SKILL.md +219 -219
- package/skills/incident/SKILL.md +254 -251
- package/skills/integrity-check/SKILL.md +169 -169
- package/skills/journal/SKILL.md +240 -238
- package/skills/launch/SKILL.md +344 -342
- package/skills/logic-guardian/SKILL.md +251 -251
- package/skills/marketing/SKILL.md +290 -245
- package/skills/mcp-builder/SKILL.md +425 -423
- package/skills/mcp-builder/references/auto-discovery-pattern.md +169 -0
- package/skills/neural-memory/SKILL.md +362 -362
- package/skills/onboard/SKILL.md +404 -403
- package/skills/perf/SKILL.md +346 -346
- package/skills/plan/SKILL.md +433 -370
- package/skills/plan/references/feature-map.md +84 -0
- package/skills/preflight/SKILL.md +415 -396
- package/skills/problem-solver/SKILL.md +380 -284
- package/skills/rescue/SKILL.md +474 -450
- package/skills/retro/SKILL.md +5 -1
- package/skills/review/SKILL.md +612 -535
- package/skills/review-intake/SKILL.md +249 -249
- package/skills/safeguard/SKILL.md +200 -200
- package/skills/sast/SKILL.md +190 -190
- package/skills/scaffold/SKILL.md +328 -286
- package/skills/scope-guard/SKILL.md +180 -162
- package/skills/scout/SKILL.md +263 -263
- package/skills/sentinel/SKILL.md +382 -353
- package/skills/sentinel-env/SKILL.md +254 -254
- package/skills/sequential-thinking/SKILL.md +234 -234
- package/skills/session-bridge/SKILL.md +543 -397
- package/skills/skill-forge/SKILL.md +581 -539
- package/skills/skill-router/{skill.md → SKILL.md} +30 -2
- package/skills/surgeon/SKILL.md +215 -215
- package/skills/team/SKILL.md +556 -514
- package/skills/test/SKILL.md +614 -587
- package/skills/trend-scout/SKILL.md +145 -145
- package/skills/verification/SKILL.md +326 -325
- package/skills/video-creator/SKILL.md +201 -201
- package/skills/watchdog/SKILL.md +168 -168
- package/skills/worktree/SKILL.md +140 -140
|
@@ -1,55 +1,55 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: "chart-components"
|
|
3
|
-
pack: "@rune/trading"
|
|
4
|
-
description: "Financial chart patterns — candlestick, line, and area charts using TradingView Lightweight Charts. Real-time update handlers, zoom, crosshair sync, indicator overlays, and responsive layout with reduced-motion support."
|
|
5
|
-
model: sonnet
|
|
6
|
-
tools: [Read, Edit, Write, Grep, Glob, Bash]
|
|
7
|
-
---
|
|
8
|
-
|
|
9
|
-
# chart-components
|
|
10
|
-
|
|
11
|
-
Financial chart patterns — candlestick, line, and area charts using TradingView Lightweight Charts. Real-time update handlers, zoom, crosshair sync, indicator overlays, and responsive layout with reduced-motion support.
|
|
12
|
-
|
|
13
|
-
#### Workflow
|
|
14
|
-
|
|
15
|
-
**Step 1 — Detect chart library and configure chart instance**
|
|
16
|
-
Use `Grep` to check for `lightweight-charts` or `@tradingview/charting_library` in `package.json`. Initialize with `createChart(container, { autoSize: true, layout: { background: { color: '#0c1419' } } })`. Create a `CandlestickSeries` with green/red up/down colors matching the project palette.
|
|
17
|
-
|
|
18
|
-
**Step 2 — Real-time update handler**
|
|
19
|
-
Subscribe to the normalized WebSocket feed from `realtime-data`. On each tick, call `series.update({ time, open, high, low, close, volume })`. Batch rapid updates with `requestAnimationFrame` to avoid layout thrashing. Use `Read` to verify the container element is stable (not re-mounting on every render).
|
|
20
|
-
|
|
21
|
-
**Step 3 — Responsive layout and reduced-motion**
|
|
22
|
-
Use `Bash` to run `window.matchMedia('(prefers-reduced-motion: reduce)')` check at init time. When true, disable chart animations (`animation: { duration: 0 }`). Add `ResizeObserver` on the container and call `chart.applyOptions({ width, height })` on size change.
|
|
23
|
-
|
|
24
|
-
#### Example
|
|
25
|
-
|
|
26
|
-
```typescript
|
|
27
|
-
import { createChart, CandlestickSeries } from 'lightweight-charts';
|
|
28
|
-
|
|
29
|
-
function initCandlestickChart(container: HTMLElement): CandlestickSeries {
|
|
30
|
-
const reducedMotion = window.matchMedia(
|
|
31
|
-
'(prefers-reduced-motion: reduce)',
|
|
32
|
-
).matches;
|
|
33
|
-
|
|
34
|
-
const chart = createChart(container, {
|
|
35
|
-
autoSize: true,
|
|
36
|
-
layout: { background: { color: '#0c1419' }, textColor: '#a0aeb8' },
|
|
37
|
-
grid: { vertLines: { color: '#2a3f52' }, horzLines: { color: '#2a3f52' } },
|
|
38
|
-
crosshair: { mode: 1 },
|
|
39
|
-
animation: { duration: reducedMotion ? 0 : 300 },
|
|
40
|
-
});
|
|
41
|
-
|
|
42
|
-
const series = chart.addSeries(CandlestickSeries, {
|
|
43
|
-
upColor: '#00d084',
|
|
44
|
-
downColor: '#ff6b6b',
|
|
45
|
-
borderVisible: false,
|
|
46
|
-
wickUpColor: '#00d084',
|
|
47
|
-
wickDownColor: '#ff6b6b',
|
|
48
|
-
});
|
|
49
|
-
|
|
50
|
-
new ResizeObserver(() => chart.applyOptions({ width: container.clientWidth }))
|
|
51
|
-
.observe(container);
|
|
52
|
-
|
|
53
|
-
return series;
|
|
54
|
-
}
|
|
55
|
-
```
|
|
1
|
+
---
|
|
2
|
+
name: "chart-components"
|
|
3
|
+
pack: "@rune/trading"
|
|
4
|
+
description: "Financial chart patterns — candlestick, line, and area charts using TradingView Lightweight Charts. Real-time update handlers, zoom, crosshair sync, indicator overlays, and responsive layout with reduced-motion support."
|
|
5
|
+
model: sonnet
|
|
6
|
+
tools: [Read, Edit, Write, Grep, Glob, Bash]
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# chart-components
|
|
10
|
+
|
|
11
|
+
Financial chart patterns — candlestick, line, and area charts using TradingView Lightweight Charts. Real-time update handlers, zoom, crosshair sync, indicator overlays, and responsive layout with reduced-motion support.
|
|
12
|
+
|
|
13
|
+
#### Workflow
|
|
14
|
+
|
|
15
|
+
**Step 1 — Detect chart library and configure chart instance**
|
|
16
|
+
Use `Grep` to check for `lightweight-charts` or `@tradingview/charting_library` in `package.json`. Initialize with `createChart(container, { autoSize: true, layout: { background: { color: '#0c1419' } } })`. Create a `CandlestickSeries` with green/red up/down colors matching the project palette.
|
|
17
|
+
|
|
18
|
+
**Step 2 — Real-time update handler**
|
|
19
|
+
Subscribe to the normalized WebSocket feed from `realtime-data`. On each tick, call `series.update({ time, open, high, low, close, volume })`. Batch rapid updates with `requestAnimationFrame` to avoid layout thrashing. Use `Read` to verify the container element is stable (not re-mounting on every render).
|
|
20
|
+
|
|
21
|
+
**Step 3 — Responsive layout and reduced-motion**
|
|
22
|
+
Use `Bash` to run `window.matchMedia('(prefers-reduced-motion: reduce)')` check at init time. When true, disable chart animations (`animation: { duration: 0 }`). Add `ResizeObserver` on the container and call `chart.applyOptions({ width, height })` on size change.
|
|
23
|
+
|
|
24
|
+
#### Example
|
|
25
|
+
|
|
26
|
+
```typescript
|
|
27
|
+
import { createChart, CandlestickSeries } from 'lightweight-charts';
|
|
28
|
+
|
|
29
|
+
function initCandlestickChart(container: HTMLElement): CandlestickSeries {
|
|
30
|
+
const reducedMotion = window.matchMedia(
|
|
31
|
+
'(prefers-reduced-motion: reduce)',
|
|
32
|
+
).matches;
|
|
33
|
+
|
|
34
|
+
const chart = createChart(container, {
|
|
35
|
+
autoSize: true,
|
|
36
|
+
layout: { background: { color: '#0c1419' }, textColor: '#a0aeb8' },
|
|
37
|
+
grid: { vertLines: { color: '#2a3f52' }, horzLines: { color: '#2a3f52' } },
|
|
38
|
+
crosshair: { mode: 1 },
|
|
39
|
+
animation: { duration: reducedMotion ? 0 : 300 },
|
|
40
|
+
});
|
|
41
|
+
|
|
42
|
+
const series = chart.addSeries(CandlestickSeries, {
|
|
43
|
+
upColor: '#00d084',
|
|
44
|
+
downColor: '#ff6b6b',
|
|
45
|
+
borderVisible: false,
|
|
46
|
+
wickUpColor: '#00d084',
|
|
47
|
+
wickDownColor: '#ff6b6b',
|
|
48
|
+
});
|
|
49
|
+
|
|
50
|
+
new ResizeObserver(() => chart.applyOptions({ width: container.clientWidth }))
|
|
51
|
+
.observe(container);
|
|
52
|
+
|
|
53
|
+
return series;
|
|
54
|
+
}
|
|
55
|
+
```
|
|
@@ -1,125 +1,125 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: "experiment-loop"
|
|
3
|
-
pack: "@rune/trading"
|
|
4
|
-
description: "Scientific method for trading strategy development — hypothesize → implement → backtest → analyze → refine. Prevents the #1 strategy development failure: changing parameters randomly without tracking what was tested, what worked, and why."
|
|
5
|
-
model: sonnet
|
|
6
|
-
tools: [Read, Edit, Write, Grep, Glob, Bash]
|
|
7
|
-
---
|
|
8
|
-
|
|
9
|
-
# experiment-loop
|
|
10
|
-
|
|
11
|
-
Scientific method for trading strategy development — hypothesize → implement → backtest → analyze → refine. Prevents the #1 strategy development failure: changing parameters randomly without tracking what was tested, what worked, and why.
|
|
12
|
-
|
|
13
|
-
#### Workflow
|
|
14
|
-
|
|
15
|
-
**Step 1 — Define hypothesis**
|
|
16
|
-
Every strategy change starts as a falsifiable hypothesis:
|
|
17
|
-
```
|
|
18
|
-
HYPOTHESIS: [What you believe]
|
|
19
|
-
EVIDENCE: [Why you believe it — chart observation, backtest anomaly, market regime]
|
|
20
|
-
TEST: [How to verify — specific backtest config, date range, token set]
|
|
21
|
-
SUCCESS CRITERIA: [Measurable threshold — "win rate > 55% AND max drawdown < 15%"]
|
|
22
|
-
FAILURE CRITERIA: [When to reject — "win rate < 45% OR drawdown > 25%"]
|
|
23
|
-
```
|
|
24
|
-
|
|
25
|
-
Check `.rune/experiments/` for prior experiments on the same component. If a similar hypothesis was already tested and rejected, flag it: "This was tested in experiment #12 and rejected because [reason]. Proceed anyway?"
|
|
26
|
-
|
|
27
|
-
**Step 2 — Implement variant**
|
|
28
|
-
Create the strategy variant in an isolated branch or config:
|
|
29
|
-
- Use `Grep` to find the parameter or logic being changed
|
|
30
|
-
- Create a named variant (e.g., `rsi_entry_v6_longer_period`) — NEVER modify the production logic directly
|
|
31
|
-
- Document the exact change: "Changed RSI period from 7 to 14, challenge threshold from 65 to 60"
|
|
32
|
-
- If logic change (not just parameter): ensure backtest engine mirrors the change (production-backtest sync from `trade-logic`)
|
|
33
|
-
|
|
34
|
-
**Step 3 — Run backtest**
|
|
35
|
-
Execute backtest against the defined test conditions:
|
|
36
|
-
- Use `Bash` to run the backtest command with the variant config
|
|
37
|
-
- Capture results: total PnL, win rate, max drawdown, Sharpe ratio, number of trades
|
|
38
|
-
- Compare against the control (current production parameters)
|
|
39
|
-
- Record execution time and date range
|
|
40
|
-
|
|
41
|
-
**Step 4 — Analyze results**
|
|
42
|
-
Structured analysis against success/failure criteria:
|
|
43
|
-
|
|
44
|
-
```
|
|
45
|
-
EXPERIMENT #14: RSI Period 14 vs 7
|
|
46
|
-
STATUS: REJECTED ❌
|
|
47
|
-
|
|
48
|
-
RESULTS:
|
|
49
|
-
| Metric | Control (v5) | Variant (v6) | Δ |
|
|
50
|
-
|---------------|-------------|-------------|---------|
|
|
51
|
-
| Total PnL | $20,445 | $18,200 | -$2,245 |
|
|
52
|
-
| Win Rate | 58.3% | 52.1% | -6.2% |
|
|
53
|
-
| Max Drawdown | 12.4% | 14.8% | +2.4% |
|
|
54
|
-
| Sharpe Ratio | 1.42 | 1.18 | -0.24 |
|
|
55
|
-
| Trade Count | 156 | 89 | -67 |
|
|
56
|
-
|
|
57
|
-
CONCLUSION: Longer RSI period reduces signal frequency by 43% without
|
|
58
|
-
improving quality. Win rate dropped below 55% threshold. REJECTED.
|
|
59
|
-
|
|
60
|
-
INSIGHT: RSI 7 captures mean-reversion signals faster on 15m timeframe.
|
|
61
|
-
Longer periods may suit 4H+ timeframes (not tested — add to backlog).
|
|
62
|
-
```
|
|
63
|
-
|
|
64
|
-
**Step 5 — Record and route**
|
|
65
|
-
Save experiment to `.rune/experiments/<number>-<name>.md`:
|
|
66
|
-
- If **ACCEPTED**: update production parameters → run `trade-logic` to sync manifest → commit
|
|
67
|
-
- If **REJECTED**: record conclusion and insight → add derived hypotheses to backlog
|
|
68
|
-
- If **INCONCLUSIVE**: define additional test conditions or longer date range → re-run
|
|
69
|
-
- Link to the experiment from `trade-logic` manifest: "RSI Entry v5: validated by experiment #14"
|
|
70
|
-
|
|
71
|
-
Update experiment index `.rune/experiments/index.md`:
|
|
72
|
-
```
|
|
73
|
-
| # | Hypothesis | Component | Status | Key Metric | Date |
|
|
74
|
-
|---|-----------|-----------|--------|------------|------|
|
|
75
|
-
| 14 | RSI 14 > RSI 7 | rsi_entry | ❌ Rejected | WR 52% < 55% | 2025-03-15 |
|
|
76
|
-
| 13 | EMA 120 wick exit | ema_follow | ✅ Accepted | PnL +$2,036 | 2025-03-10 |
|
|
77
|
-
```
|
|
78
|
-
|
|
79
|
-
#### Example
|
|
80
|
-
|
|
81
|
-
```python
|
|
82
|
-
# Experiment runner pattern
|
|
83
|
-
from dataclasses import dataclass
|
|
84
|
-
from decimal import Decimal
|
|
85
|
-
|
|
86
|
-
@dataclass(frozen=True)
|
|
87
|
-
class ExperimentConfig:
|
|
88
|
-
name: str
|
|
89
|
-
hypothesis: str
|
|
90
|
-
variant_params: dict[str, str | int | float]
|
|
91
|
-
control_params: dict[str, str | int | float]
|
|
92
|
-
date_range: tuple[str, str]
|
|
93
|
-
tokens: list[str]
|
|
94
|
-
success_criteria: dict[str, tuple[str, float]] # metric: (operator, threshold)
|
|
95
|
-
|
|
96
|
-
@dataclass(frozen=True)
|
|
97
|
-
class ExperimentResult:
|
|
98
|
-
config: ExperimentConfig
|
|
99
|
-
control_metrics: dict[str, Decimal]
|
|
100
|
-
variant_metrics: dict[str, Decimal]
|
|
101
|
-
status: str # 'accepted' | 'rejected' | 'inconclusive'
|
|
102
|
-
conclusion: str
|
|
103
|
-
insights: list[str]
|
|
104
|
-
|
|
105
|
-
def evaluate_experiment(result: ExperimentResult) -> str:
|
|
106
|
-
"""Evaluate variant against success criteria."""
|
|
107
|
-
for metric, (op, threshold) in result.config.success_criteria.items():
|
|
108
|
-
variant_val = result.variant_metrics.get(metric, Decimal('0'))
|
|
109
|
-
if op == '>' and variant_val <= Decimal(str(threshold)):
|
|
110
|
-
return 'rejected'
|
|
111
|
-
if op == '<' and variant_val >= Decimal(str(threshold)):
|
|
112
|
-
return 'rejected'
|
|
113
|
-
return 'accepted'
|
|
114
|
-
|
|
115
|
-
# Usage:
|
|
116
|
-
# config = ExperimentConfig(
|
|
117
|
-
# name="rsi_period_14",
|
|
118
|
-
# hypothesis="RSI 14 captures better signals than RSI 7 on 15m",
|
|
119
|
-
# variant_params={"rsi_period": 14, "challenge_threshold": 60},
|
|
120
|
-
# control_params={"rsi_period": 7, "challenge_threshold": 65},
|
|
121
|
-
# date_range=("2024-09-01", "2025-03-01"),
|
|
122
|
-
# tokens=["BTCUSDT", "ETHUSDT", "SOLUSDT"],
|
|
123
|
-
# success_criteria={"win_rate": (">", 0.55), "max_drawdown": ("<", 0.15)},
|
|
124
|
-
# )
|
|
125
|
-
```
|
|
1
|
+
---
|
|
2
|
+
name: "experiment-loop"
|
|
3
|
+
pack: "@rune/trading"
|
|
4
|
+
description: "Scientific method for trading strategy development — hypothesize → implement → backtest → analyze → refine. Prevents the #1 strategy development failure: changing parameters randomly without tracking what was tested, what worked, and why."
|
|
5
|
+
model: sonnet
|
|
6
|
+
tools: [Read, Edit, Write, Grep, Glob, Bash]
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# experiment-loop
|
|
10
|
+
|
|
11
|
+
Scientific method for trading strategy development — hypothesize → implement → backtest → analyze → refine. Prevents the #1 strategy development failure: changing parameters randomly without tracking what was tested, what worked, and why.
|
|
12
|
+
|
|
13
|
+
#### Workflow
|
|
14
|
+
|
|
15
|
+
**Step 1 — Define hypothesis**
|
|
16
|
+
Every strategy change starts as a falsifiable hypothesis:
|
|
17
|
+
```
|
|
18
|
+
HYPOTHESIS: [What you believe]
|
|
19
|
+
EVIDENCE: [Why you believe it — chart observation, backtest anomaly, market regime]
|
|
20
|
+
TEST: [How to verify — specific backtest config, date range, token set]
|
|
21
|
+
SUCCESS CRITERIA: [Measurable threshold — "win rate > 55% AND max drawdown < 15%"]
|
|
22
|
+
FAILURE CRITERIA: [When to reject — "win rate < 45% OR drawdown > 25%"]
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
Check `.rune/experiments/` for prior experiments on the same component. If a similar hypothesis was already tested and rejected, flag it: "This was tested in experiment #12 and rejected because [reason]. Proceed anyway?"
|
|
26
|
+
|
|
27
|
+
**Step 2 — Implement variant**
|
|
28
|
+
Create the strategy variant in an isolated branch or config:
|
|
29
|
+
- Use `Grep` to find the parameter or logic being changed
|
|
30
|
+
- Create a named variant (e.g., `rsi_entry_v6_longer_period`) — NEVER modify the production logic directly
|
|
31
|
+
- Document the exact change: "Changed RSI period from 7 to 14, challenge threshold from 65 to 60"
|
|
32
|
+
- If logic change (not just parameter): ensure backtest engine mirrors the change (production-backtest sync from `trade-logic`)
|
|
33
|
+
|
|
34
|
+
**Step 3 — Run backtest**
|
|
35
|
+
Execute backtest against the defined test conditions:
|
|
36
|
+
- Use `Bash` to run the backtest command with the variant config
|
|
37
|
+
- Capture results: total PnL, win rate, max drawdown, Sharpe ratio, number of trades
|
|
38
|
+
- Compare against the control (current production parameters)
|
|
39
|
+
- Record execution time and date range
|
|
40
|
+
|
|
41
|
+
**Step 4 — Analyze results**
|
|
42
|
+
Structured analysis against success/failure criteria:
|
|
43
|
+
|
|
44
|
+
```
|
|
45
|
+
EXPERIMENT #14: RSI Period 14 vs 7
|
|
46
|
+
STATUS: REJECTED ❌
|
|
47
|
+
|
|
48
|
+
RESULTS:
|
|
49
|
+
| Metric | Control (v5) | Variant (v6) | Δ |
|
|
50
|
+
|---------------|-------------|-------------|---------|
|
|
51
|
+
| Total PnL | $20,445 | $18,200 | -$2,245 |
|
|
52
|
+
| Win Rate | 58.3% | 52.1% | -6.2% |
|
|
53
|
+
| Max Drawdown | 12.4% | 14.8% | +2.4% |
|
|
54
|
+
| Sharpe Ratio | 1.42 | 1.18 | -0.24 |
|
|
55
|
+
| Trade Count | 156 | 89 | -67 |
|
|
56
|
+
|
|
57
|
+
CONCLUSION: Longer RSI period reduces signal frequency by 43% without
|
|
58
|
+
improving quality. Win rate dropped below 55% threshold. REJECTED.
|
|
59
|
+
|
|
60
|
+
INSIGHT: RSI 7 captures mean-reversion signals faster on 15m timeframe.
|
|
61
|
+
Longer periods may suit 4H+ timeframes (not tested — add to backlog).
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
**Step 5 — Record and route**
|
|
65
|
+
Save experiment to `.rune/experiments/<number>-<name>.md`:
|
|
66
|
+
- If **ACCEPTED**: update production parameters → run `trade-logic` to sync manifest → commit
|
|
67
|
+
- If **REJECTED**: record conclusion and insight → add derived hypotheses to backlog
|
|
68
|
+
- If **INCONCLUSIVE**: define additional test conditions or longer date range → re-run
|
|
69
|
+
- Link to the experiment from `trade-logic` manifest: "RSI Entry v5: validated by experiment #14"
|
|
70
|
+
|
|
71
|
+
Update experiment index `.rune/experiments/index.md`:
|
|
72
|
+
```
|
|
73
|
+
| # | Hypothesis | Component | Status | Key Metric | Date |
|
|
74
|
+
|---|-----------|-----------|--------|------------|------|
|
|
75
|
+
| 14 | RSI 14 > RSI 7 | rsi_entry | ❌ Rejected | WR 52% < 55% | 2025-03-15 |
|
|
76
|
+
| 13 | EMA 120 wick exit | ema_follow | ✅ Accepted | PnL +$2,036 | 2025-03-10 |
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
#### Example
|
|
80
|
+
|
|
81
|
+
```python
|
|
82
|
+
# Experiment runner pattern
|
|
83
|
+
from dataclasses import dataclass
|
|
84
|
+
from decimal import Decimal
|
|
85
|
+
|
|
86
|
+
@dataclass(frozen=True)
|
|
87
|
+
class ExperimentConfig:
|
|
88
|
+
name: str
|
|
89
|
+
hypothesis: str
|
|
90
|
+
variant_params: dict[str, str | int | float]
|
|
91
|
+
control_params: dict[str, str | int | float]
|
|
92
|
+
date_range: tuple[str, str]
|
|
93
|
+
tokens: list[str]
|
|
94
|
+
success_criteria: dict[str, tuple[str, float]] # metric: (operator, threshold)
|
|
95
|
+
|
|
96
|
+
@dataclass(frozen=True)
|
|
97
|
+
class ExperimentResult:
|
|
98
|
+
config: ExperimentConfig
|
|
99
|
+
control_metrics: dict[str, Decimal]
|
|
100
|
+
variant_metrics: dict[str, Decimal]
|
|
101
|
+
status: str # 'accepted' | 'rejected' | 'inconclusive'
|
|
102
|
+
conclusion: str
|
|
103
|
+
insights: list[str]
|
|
104
|
+
|
|
105
|
+
def evaluate_experiment(result: ExperimentResult) -> str:
|
|
106
|
+
"""Evaluate variant against success criteria."""
|
|
107
|
+
for metric, (op, threshold) in result.config.success_criteria.items():
|
|
108
|
+
variant_val = result.variant_metrics.get(metric, Decimal('0'))
|
|
109
|
+
if op == '>' and variant_val <= Decimal(str(threshold)):
|
|
110
|
+
return 'rejected'
|
|
111
|
+
if op == '<' and variant_val >= Decimal(str(threshold)):
|
|
112
|
+
return 'rejected'
|
|
113
|
+
return 'accepted'
|
|
114
|
+
|
|
115
|
+
# Usage:
|
|
116
|
+
# config = ExperimentConfig(
|
|
117
|
+
# name="rsi_period_14",
|
|
118
|
+
# hypothesis="RSI 14 captures better signals than RSI 7 on 15m",
|
|
119
|
+
# variant_params={"rsi_period": 14, "challenge_threshold": 60},
|
|
120
|
+
# control_params={"rsi_period": 7, "challenge_threshold": 65},
|
|
121
|
+
# date_range=("2024-09-01", "2025-03-01"),
|
|
122
|
+
# tokens=["BTCUSDT", "ETHUSDT", "SOLUSDT"],
|
|
123
|
+
# success_criteria={"win_rate": (">", 0.55), "max_drawdown": ("<", 0.15)},
|
|
124
|
+
# )
|
|
125
|
+
```
|
|
@@ -1,47 +1,47 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: "fintech-patterns"
|
|
3
|
-
pack: "@rune/trading"
|
|
4
|
-
description: "Financial application patterns — safe money handling with Decimal/BigInt, transaction processing, audit trails, regulatory compliance, and PnL calculations."
|
|
5
|
-
model: sonnet
|
|
6
|
-
tools: [Read, Edit, Write, Grep, Glob, Bash]
|
|
7
|
-
---
|
|
8
|
-
|
|
9
|
-
# fintech-patterns
|
|
10
|
-
|
|
11
|
-
Financial application patterns — safe money handling with Decimal/BigInt, transaction processing, audit trails, regulatory compliance, and PnL calculations. Prevents the #1 fintech bug: float arithmetic on money.
|
|
12
|
-
|
|
13
|
-
#### Workflow
|
|
14
|
-
|
|
15
|
-
**Step 1 — Detect money handling code**
|
|
16
|
-
Use `Grep` to scan for raw float arithmetic on price/amount/balance fields: `Grep pattern="(price|amount|balance|pnl)\s*[\+\-\*\/]" glob="**/*.ts"`. Flag any result not wrapped in Decimal or BigInt.
|
|
17
|
-
|
|
18
|
-
**Step 2 — Enforce Decimal/BigInt boundaries**
|
|
19
|
-
Use `Read` on each flagged file to identify entry points (API response parsing, user input). Replace raw number literals with `new Decimal(value)` at parse time. All arithmetic must flow through Decimal operations until final display.
|
|
20
|
-
|
|
21
|
-
**Step 3 — Implement audit trail and verify rounding**
|
|
22
|
-
Use `Bash` to run `tsc --noEmit` confirming no implicit `any` on financial fields. Add an immutable audit log entry on every mutation (create, fill, cancel). Verify rounding mode is `ROUND_HALF_EVEN` (banker's rounding) for all display formatting.
|
|
23
|
-
|
|
24
|
-
#### Example
|
|
25
|
-
|
|
26
|
-
```typescript
|
|
27
|
-
import Decimal from 'decimal.js';
|
|
28
|
-
|
|
29
|
-
Decimal.set({ rounding: Decimal.ROUND_HALF_EVEN });
|
|
30
|
-
|
|
31
|
-
// NEVER: const fee = price * 0.001
|
|
32
|
-
// ALWAYS: Decimal arithmetic — exact, auditable
|
|
33
|
-
function calculateFee(price: string, quantity: string, feeRate: string): Decimal {
|
|
34
|
-
return new Decimal(price)
|
|
35
|
-
.times(new Decimal(quantity))
|
|
36
|
-
.times(new Decimal(feeRate))
|
|
37
|
-
.toDecimalPlaces(8);
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
function formatUSD(value: Decimal): string {
|
|
41
|
-
return new Intl.NumberFormat('en-US', {
|
|
42
|
-
style: 'currency',
|
|
43
|
-
currency: 'USD',
|
|
44
|
-
minimumFractionDigits: 2,
|
|
45
|
-
}).format(value.toNumber());
|
|
46
|
-
}
|
|
47
|
-
```
|
|
1
|
+
---
|
|
2
|
+
name: "fintech-patterns"
|
|
3
|
+
pack: "@rune/trading"
|
|
4
|
+
description: "Financial application patterns — safe money handling with Decimal/BigInt, transaction processing, audit trails, regulatory compliance, and PnL calculations."
|
|
5
|
+
model: sonnet
|
|
6
|
+
tools: [Read, Edit, Write, Grep, Glob, Bash]
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# fintech-patterns
|
|
10
|
+
|
|
11
|
+
Financial application patterns — safe money handling with Decimal/BigInt, transaction processing, audit trails, regulatory compliance, and PnL calculations. Prevents the #1 fintech bug: float arithmetic on money.
|
|
12
|
+
|
|
13
|
+
#### Workflow
|
|
14
|
+
|
|
15
|
+
**Step 1 — Detect money handling code**
|
|
16
|
+
Use `Grep` to scan for raw float arithmetic on price/amount/balance fields: `Grep pattern="(price|amount|balance|pnl)\s*[\+\-\*\/]" glob="**/*.ts"`. Flag any result not wrapped in Decimal or BigInt.
|
|
17
|
+
|
|
18
|
+
**Step 2 — Enforce Decimal/BigInt boundaries**
|
|
19
|
+
Use `Read` on each flagged file to identify entry points (API response parsing, user input). Replace raw number literals with `new Decimal(value)` at parse time. All arithmetic must flow through Decimal operations until final display.
|
|
20
|
+
|
|
21
|
+
**Step 3 — Implement audit trail and verify rounding**
|
|
22
|
+
Use `Bash` to run `tsc --noEmit` confirming no implicit `any` on financial fields. Add an immutable audit log entry on every mutation (create, fill, cancel). Verify rounding mode is `ROUND_HALF_EVEN` (banker's rounding) for all display formatting.
|
|
23
|
+
|
|
24
|
+
#### Example
|
|
25
|
+
|
|
26
|
+
```typescript
|
|
27
|
+
import Decimal from 'decimal.js';
|
|
28
|
+
|
|
29
|
+
Decimal.set({ rounding: Decimal.ROUND_HALF_EVEN });
|
|
30
|
+
|
|
31
|
+
// NEVER: const fee = price * 0.001
|
|
32
|
+
// ALWAYS: Decimal arithmetic — exact, auditable
|
|
33
|
+
function calculateFee(price: string, quantity: string, feeRate: string): Decimal {
|
|
34
|
+
return new Decimal(price)
|
|
35
|
+
.times(new Decimal(quantity))
|
|
36
|
+
.times(new Decimal(feeRate))
|
|
37
|
+
.toDecimalPlaces(8);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
function formatUSD(value: Decimal): string {
|
|
41
|
+
return new Intl.NumberFormat('en-US', {
|
|
42
|
+
style: 'currency',
|
|
43
|
+
currency: 'USD',
|
|
44
|
+
minimumFractionDigits: 2,
|
|
45
|
+
}).format(value.toNumber());
|
|
46
|
+
}
|
|
47
|
+
```
|
|
@@ -1,58 +1,58 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: "indicator-library"
|
|
3
|
-
pack: "@rune/trading"
|
|
4
|
-
description: "Technical indicator implementations — SMA, EMA, RSI, MACD, Bollinger Bands, VWAP. Streaming calculation patterns that update incrementally on each new tick rather than recomputing the full history."
|
|
5
|
-
model: sonnet
|
|
6
|
-
tools: [Read, Edit, Write, Grep, Glob, Bash]
|
|
7
|
-
---
|
|
8
|
-
|
|
9
|
-
# indicator-library
|
|
10
|
-
|
|
11
|
-
Technical indicator implementations — SMA, EMA, RSI, MACD, Bollinger Bands, VWAP. Streaming calculation patterns that update incrementally on each new tick rather than recomputing the full history.
|
|
12
|
-
|
|
13
|
-
#### Workflow
|
|
14
|
-
|
|
15
|
-
**Step 1 — Select indicators and initialize state**
|
|
16
|
-
Use `Read` on the product spec or existing chart config to identify required indicators. For each, allocate a rolling window buffer sized to the longest period (e.g., 200 for SMA-200). Initialize with historical OHLCV data fetched via REST before the WebSocket feed opens.
|
|
17
|
-
|
|
18
|
-
**Step 2 — Streaming incremental calculation**
|
|
19
|
-
On each new tick from `realtime-data`, push the close price into the rolling buffer and evict the oldest value. Recompute only the current indicator value — not the full series. For RSI, maintain running average gains/losses using Wilder smoothing. Use `Bash` to run unit tests comparing streaming output against a reference batch computation.
|
|
20
|
-
|
|
21
|
-
**Step 3 — Overlay on chart component**
|
|
22
|
-
Create a `LineSeries` on the chart instance from `chart-components` for each indicator. On each streaming update, call `indicatorSeries.update({ time, value })`. Use `Grep` to confirm indicator series are cleaned up (`chart.removeSeries(s)`) when the symbol or timeframe changes to prevent memory leaks.
|
|
23
|
-
|
|
24
|
-
#### Example
|
|
25
|
-
|
|
26
|
-
```typescript
|
|
27
|
-
class StreamingSMA {
|
|
28
|
-
private readonly window: number[] = [];
|
|
29
|
-
|
|
30
|
-
constructor(private readonly period: number) {}
|
|
31
|
-
|
|
32
|
-
update(price: number): number | null {
|
|
33
|
-
this.window.push(price);
|
|
34
|
-
if (this.window.length > this.period) {
|
|
35
|
-
this.window.shift();
|
|
36
|
-
}
|
|
37
|
-
if (this.window.length < this.period) return null;
|
|
38
|
-
const sum = this.window.reduce((acc, v) => acc + v, 0);
|
|
39
|
-
return sum / this.period;
|
|
40
|
-
}
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
class StreamingEMA {
|
|
44
|
-
private ema: number | null = null;
|
|
45
|
-
private readonly k: number;
|
|
46
|
-
|
|
47
|
-
constructor(private readonly period: number) {
|
|
48
|
-
this.k = 2 / (period + 1);
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
update(price: number): number | null {
|
|
52
|
-
this.ema = this.ema === null
|
|
53
|
-
? price
|
|
54
|
-
: price * this.k + this.ema * (1 - this.k);
|
|
55
|
-
return this.ema;
|
|
56
|
-
}
|
|
57
|
-
}
|
|
58
|
-
```
|
|
1
|
+
---
|
|
2
|
+
name: "indicator-library"
|
|
3
|
+
pack: "@rune/trading"
|
|
4
|
+
description: "Technical indicator implementations — SMA, EMA, RSI, MACD, Bollinger Bands, VWAP. Streaming calculation patterns that update incrementally on each new tick rather than recomputing the full history."
|
|
5
|
+
model: sonnet
|
|
6
|
+
tools: [Read, Edit, Write, Grep, Glob, Bash]
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# indicator-library
|
|
10
|
+
|
|
11
|
+
Technical indicator implementations — SMA, EMA, RSI, MACD, Bollinger Bands, VWAP. Streaming calculation patterns that update incrementally on each new tick rather than recomputing the full history.
|
|
12
|
+
|
|
13
|
+
#### Workflow
|
|
14
|
+
|
|
15
|
+
**Step 1 — Select indicators and initialize state**
|
|
16
|
+
Use `Read` on the product spec or existing chart config to identify required indicators. For each, allocate a rolling window buffer sized to the longest period (e.g., 200 for SMA-200). Initialize with historical OHLCV data fetched via REST before the WebSocket feed opens.
|
|
17
|
+
|
|
18
|
+
**Step 2 — Streaming incremental calculation**
|
|
19
|
+
On each new tick from `realtime-data`, push the close price into the rolling buffer and evict the oldest value. Recompute only the current indicator value — not the full series. For RSI, maintain running average gains/losses using Wilder smoothing. Use `Bash` to run unit tests comparing streaming output against a reference batch computation.
|
|
20
|
+
|
|
21
|
+
**Step 3 — Overlay on chart component**
|
|
22
|
+
Create a `LineSeries` on the chart instance from `chart-components` for each indicator. On each streaming update, call `indicatorSeries.update({ time, value })`. Use `Grep` to confirm indicator series are cleaned up (`chart.removeSeries(s)`) when the symbol or timeframe changes to prevent memory leaks.
|
|
23
|
+
|
|
24
|
+
#### Example
|
|
25
|
+
|
|
26
|
+
```typescript
|
|
27
|
+
class StreamingSMA {
|
|
28
|
+
private readonly window: number[] = [];
|
|
29
|
+
|
|
30
|
+
constructor(private readonly period: number) {}
|
|
31
|
+
|
|
32
|
+
update(price: number): number | null {
|
|
33
|
+
this.window.push(price);
|
|
34
|
+
if (this.window.length > this.period) {
|
|
35
|
+
this.window.shift();
|
|
36
|
+
}
|
|
37
|
+
if (this.window.length < this.period) return null;
|
|
38
|
+
const sum = this.window.reduce((acc, v) => acc + v, 0);
|
|
39
|
+
return sum / this.period;
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
class StreamingEMA {
|
|
44
|
+
private ema: number | null = null;
|
|
45
|
+
private readonly k: number;
|
|
46
|
+
|
|
47
|
+
constructor(private readonly period: number) {
|
|
48
|
+
this.k = 2 / (period + 1);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
update(price: number): number | null {
|
|
52
|
+
this.ema = this.ema === null
|
|
53
|
+
? price
|
|
54
|
+
: price * this.k + this.ema * (1 - this.k);
|
|
55
|
+
return this.ema;
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
```
|