run_walk_forward
Walk a profile forward over its anchored out-of-sample windows on the datahub and get the stitched OOS report back.
Runs an anchored out-of-sample walk-forward on the remote vike-datahub server and returns the
stitched WalkForwardReport. This is the tool that asks whether a sweep's winner was an edge or a
fit: a grid search returns its best row either way.
Input
| Field | Type | Required | Meaning |
|---|---|---|---|
profile | string | yes | Profile TOML with [data], [strategy] and [walkforward] (plus optional [engine]) |
script | string | no | Rhai source, injected as [strategy.params].src |
There is no split-count argument. The count rides in the profile, as [walkforward].n_splits,
a first-class section like [sweep] — so one file describes the whole run and the same text can
be shipped verbatim to a remote runner, which is the point of the compute-to-data verb. A profile
with no [walkforward] table is a clean server-side error that quotes the two lines to add;
n_splits must be at least 1, and BacktestProfile::validate rejects 0 at load.
Only the split count is configurable, deliberately: the mode is always WalkMode::Anchored and
the annualization is derived by periods_per_year. Those are the same two derivations the
Studio's walk-forward makes, so a profile cannot disagree with the Studio about what
"walk-forward" means.
{"jsonrpc":"2.0","id":3,"method":"tools/call","params":{"name":"run_walk_forward","arguments":{
"profile": "[data]\nvenue = \"binance\"\nsymbols = [\"BTCUSDT\"]\nkind = \"bar\"\ninterval = \"1d\"\nfrom = \"2023-01-01T00\"\nto = \"2024-06-01T00\"\n\n[strategy]\nname = \"buy_hold\"\n\n[walkforward]\nn_splits = 4\n"
}}}Bar mode, one series, by construction
walk_forward_strategy splits a single &[Bar] series by index, so a tick-mode or multi-symbol
profile is a clean validation error — never a silent fall back to the first symbol. Every
precondition is checked before the window loop, because the loop's closure cannot return one.
What the profile route buys over the Studio's DTO-shaped walk-forward is the whole [engine]
surface: the fee schedule, [engine.impact], [engine.resolution], [risk],
snap_to_properties, attach_funding — instead of the three flat cash/fee_rate/slippage
scalars a wire DTO can carry. The strategy resolves through the same strategy_by_name registry a
plain run uses — once up front as a pre-flight, so a bad name fails before the window loop, then
rebuilt inside the closure because each window needs a fresh strategy — the bars are loaded
through the same helpers, and each window is a fresh run at engine.cash, so a walk-forward can
never disagree with a single backtest about what the profile's [engine] meant.
What comes back
{ "walkforward": … } wrapping a WalkForwardReport:
| Field | Meaning |
|---|---|
windows | one entry per OOS window: test_range as (start, end) bar indices, and that window's oos_return |
oos_equity_curve | every window's curve rebased onto one running equity |
oos_return | the stitched fractional return over the whole walk |
oos_sharpe | Sharpe of the stitched curve, under the derived annualization |
wf_consistency | the fraction of windows that were profitable out of sample |
The stitch is what makes the curve readable as one line: each window runs fresh at engine.cash,
and its curve is rebased onto the running equity that the previous window ended at. So
oos_return compounds the windows rather than averaging them, and wf_consistency answers the
different question — how many windows worked, not how much they made. A strategy with one
enormous window and three losing ones has a good oos_return and a wf_consistency of 0.25, and
the second number is the one that should stop you.
Read wf_consistency as the overfitting input, not as a score
It is the input the overfitting verdict consumes, not a verdict itself. The anti-overfitting
statistics live in analytics/overfitting; walk-forward
supplies them with honest out-of-sample windows.
Failure modes
Identical to the other two run tools. The profile ships verbatim, so a shape error surfaces from
the server as profile parse/validate failed: … and arrives as an isError result; an
unreachable datahub is cannot connect to datahub at … and never a panic
(remote_run_tools_without_a_reachable_datahub_are_clean_errors); and every Run* verb is
control scope on the server because it compiles client-supplied Rhai, so a keyed datahub refuses
this tool at connect rather than one round trip later.
The prompt
Walk this strategy forward over four anchored splits and tell me whether the edge holds out of sample.
The natural order is run_sweep to find a candidate, then this to
test it. Walk-forward is the concept page,
vike-cli walkforward the human twin, and Sweep and
walk-forward the worked run.
run_sweep
Expand a profile's parameter grid on the datahub and get every point back ranked best-first, each with its own report.
submit_order
Place one order on a running vike-tradehub node — preview first, execute only on a second call carrying both confirm true and the single-use preview_token that preview returned.