MCP Tool Reference

The complete surface of the Folio Lab MCP server: 43 tools and 5 resources. For each tool, this page gives the OAuth scope it checks, the MCP annotations it declares, its main arguments and what it is for. The AI assistants overview covers how to connect.

How to Read the Tables

  • Scope is the OAuth scope the token must carry. The server defines six: runs:read, runs:write, analytics:read, templates:read, catalog:read and docs:read.
  • Hints are the MCP tool annotations. read-only changes nothing. destructive tells a client that the tool changes account state and should be confirmed. idempotent means a repeat call has no further effect. open world means the tool reads an outside source, such as a market data provider or the live docs site.
  • Arguments list the main parameters. Every constrained parameter publishes its full list of legal values in the tool schema.

Find securities and funds

Call these before a submission. The submission tools take exact symbols and scheme codes, and an assistant should never guess one.

ToolScopeHintsArgumentsPurpose
search_stockscatalog:readread-onlyquery, exchange, limitResolve a company name or partial symbol to NSE and BSE listings.
resolve_tickercatalog:readread-onlyname_or_symbol, exchangeThe single best listing for one name, NSE preferred when both list it. Returns no match rather than a guess.
search_us_stockscatalog:readread-only, open worldqueryResolve a company name or partial ticker to NYSE and NASDAQ equities.
search_mutual_fundscatalog:readread-only, open worldquery, asset_class, limitFind Indian mutual funds by name and return the AMFI scheme_code a fund run takes.
import_holdingscatalog:readread-only, open worldsheets or file_base64 (one of the two)Read a Zerodha or Groww holdings export into two separate starting portfolios, stocks and funds, each with submit_arguments to pass to submit_optimization. Lists what it excluded and what it could not match, with their weights. The file is at most 2 MB.

Constraints

Read config://constraint_capability before offering a constrained portfolio: not every method can enforce every family of rule.

ToolScopeHintsArgumentsPurpose
preview_constraintsruns:writeread-onlytickers, constraints, exchangeCheck rules against a universe before a run is spent: whether they can be stated, whether any portfolio satisfies all of them together, and what each group can reach under the others. Uses no run and no quota.
list_classification_mapsruns:readread-onlynoneEvery saved classification list on the account, with the map_id a constraint block's saved_classifications field takes. Reading only: a list cannot be created or edited over MCP.

Submit and manage runs

Each submission returns an id at once and runs asynchronously. Poll the matching status tool, then read the result.

ToolScopeHintsArgumentsPurpose
submit_optimizationruns:writedestructivetickers or mutual_funds, methods, benchmark, benchmark_basis, exchange, rolling_backtest and its fields, constraints, mode, current_weightsOptimize Indian stocks or Indian equity mutual funds, never both in one run. Can carry an inline walk-forward backtest for the portfolio being optimized now.
submit_us_optimizationruns:writedestructivetickers, methods, benchmark, risk_free_tenor, rolling_backtest and its fields, constraintsOptimize NYSE and NASDAQ equities. A run cannot mix US and Indian assets.
submit_backtestruns:writedestructiverun_id, methods, rebalance_frequency, window_type, window_length_yearsA standalone walk-forward backtest against a succeeded run, on that run's frozen inputs. Use this, not a second submit_optimization, to backtest a run that already exists.
submit_monte_carloruns:writedestructiverun_id, method, horizon_years, path_count, cash flows, goal, return_process, scenarios, rebalance_mode, tax, inflation, seed and further settingsA forward Monte Carlo simulation on a succeeded run of Indian stocks. Every probability is conditional on the selected model, the frozen inputs, the configuration, the engine version and the seed.
cancel_jobruns:writedestructiverun_id, kindCancel one queued or running optimization, simulation or backtest. A job that already finished returns 409.
rename_runruns:writedestructive, idempotentrun_id, nameSet a display name of at most 120 characters. An empty name restores the default.
tag_runruns:writewrite, idempotentrun_id, tag_name, tag_colorAttach a tag to a run. Tagging twice has the effect of tagging once.
untag_runruns:writedestructive, idempotentrun_id, tag_nameRemove one tag from a run. Returns 404 when the tag was not applied.
delete_runruns:writedestructiverun_idPermanently delete a run and everything attached to it: simulations, backtests, artifacts, metrics, weights, tags and comparison membership. It cannot be undone and it does not return quota.

Status, results and history

Every run-related response carries a result_url. An assistant should show it as a link: the web page is the full interactive view.

ToolScopeHintsArgumentsPurpose
get_job_statusruns:readread-onlyrun_idPoll an optimization run's lifecycle state.
get_job_resultruns:readread-onlyrun_id, include, methodsWeights, metrics and per-asset statistics of a succeeded run, with a compact headline block. include and methods narrow the payload.
get_job_configruns:readread-onlyrun_idThe inputs a run was submitted with. For reading back, not for resubmitting.
list_recent_runsruns:readread-onlylimit, cursor, search, status, tag, market, mode, constraintsOptimization runs, newest first, cursor paginated, with facet filters.
list_active_jobsruns:readread-onlynoneEverything still queued or running, across all three job kinds.
get_monte_carlo_resultruns:readread-onlymc_run_idStatus and results of one simulation, with the interpretation lines and the assumptions block that must be presented together with any probability.
list_monte_carlo_runsruns:readread-onlyrun_idThe simulations of one parent run, newest first.
list_all_monte_carlo_runsruns:readread-onlylimit (1 to 100, default 20), cursorEvery simulation on the account, with its parent run id and name.
get_backtest_resultruns:readread-onlybacktest_run_idPer-period weights and turnover, out-of-sample metrics and Sharpe inference of one standalone backtest.
list_backtest_runsruns:readread-onlyrun_idThe standalone backtests of one parent run, newest first.
list_all_backtest_runsruns:readread-onlylimit (1 to 100, default 20), cursorEvery standalone backtest on the account, with its parent run id and name.
list_run_tagsruns:readread-onlynoneEvery tag in use on the account, with its colour and the number of runs that carry it.
list_templatestemplates:readread-onlynoneThe saved optimization templates on the account.

Compare and analyse

In-sample optimizer metrics and out-of-sample backtest metrics are different populations. These tools keep them apart through kind.

ToolScopeHintsArgumentsPurpose
compare_runsruns:readread-onlyrun_ids, metrics, kind, page_size, cursor, detail, groups, curve_methodsSide-by-side metrics for up to 5 runs at once, or up to 100 in pages, or a run against its backtest.
search_runs_by_metricruns:readread-onlymetric, operator (gt, gte, lt, lte), value, limit, kind, market, mode, constraintsRuns whose metric passes a threshold. There is no equality operator: bracket a value with gte and lte.
get_analytics_summaryanalytics:readread-onlymarket, mode, constraints, benchmark, basis, tag, date_from, date_toCross-run totals and per-method aggregates. Pass market: Indian and US runs use different currencies, benchmarks and risk-free rates.
explain_metriccatalog:readread-onlymetric_nameA short explanation of a metric, with its docs URL and up to three related pages. Accepts keys and common names.

Charts, reports and files

Chart tools return JSON arrays under 25 KB for the assistant to draw. The server never returns an image.

ToolScopeHintsArgumentsPurpose
get_chart_dataruns:readread-only, open worldrun_id, chart (weights, metrics, cumulative_returns, backtest), top_n, methods, run_idsA chart packet for an optimization run. backtest is available only for a run submitted with an inline rolling backtest.
get_backtest_chart_dataruns:readread-only, open worldbacktest_run_id, methodsThe walk-forward equity curve of one standalone backtest, one point per rebalance period, with the benchmark rebased to the start.
get_monte_carlo_chart_dataruns:readread-only, open worldmc_run_id, chart (eleven packets), basis, metric, viewA chart packet for a succeeded simulation: wealth_fan, goal_probability, terminal_quantiles, path_metric, drawdown_state, scenarios, metric_suite, weight_paths, goal_ladder, annualized_return or paired_comparison.
get_run_artifactsruns:readread-onlyrun_idEvery stored artifact of a run, each with a signed download URL valid for one hour.
request_pdf_reportruns:writedestructiverun_id, kind (optimization, monte_carlo, backtest)Start PDF generation for one report. Idempotent: a report that exists returns ready, and a request for one that cannot exist yet has no effect.
get_report_statusruns:readread-onlyrun_id, kindabsent, queued, rendering, ready or failed. Poll this rather than requesting the report again.
get_report_filesruns:writewriterun_id, generate_missing_pdf, kindsOne-hour download links for each report's PDF and Excel file. It can start a missing PDF, which is why it needs the write scope.

Documentation

For a conceptual question an assistant should cite these pages rather than answer from memory.

ToolScopeHintsArgumentsPurpose
list_docsdocs:readread-onlysectionDocumentation pages with canonical URLs, optionally for one section.
search_docsdocs:readread-onlyquery, section, limitRanked pages for a query, with the full URL to cite.
get_docdocs:readread-only, open worldpath_or_urlThe live content of one docs page. Refuses a URL outside the docs.

Resources

Each resource is generated from the server-side definition it describes, so a new method or benchmark cannot be missing from it.

URIContents
config://methodsEvery selectable optimization method, with a one-line description of each.
config://benchmarksEvery Indian benchmark key, with its index name.
config://us_benchmarksThe three US benchmarks: sp500, nasdaq_100 and russell_3000, each a total-return series through an exchange-traded fund.
config://constraint_capabilityFor each method and each family of rule (per-name bounds, group sums, each_member): direct, or unsupported with the reason. The same table the web app and the report attestation read.
config://fund_manager_modeWhat mode="fund_manager" enforces, what it does not provide, its Enterprise entitlement and its default benchmark. Read it before offering the mode.

Plan Gates

A plan gate applies when a tool spends something or uses a gated capability. Reading a run that already exists is never gated, even after a plan changes.

ToolGate
Any toolA Pro or Enterprise plan. The connection is refused for a Free account.
submit_optimizationThe monthly optimization quota: Pro 50, Enterprise unlimited. mutual_funds needs a plan with fund runs. constraints needs Enterprise. mode="fund_manager" needs Enterprise. current_weights needs Pro or Enterprise.
submit_us_optimizationPro or Enterprise, and the same monthly optimization quota. constraints needs Enterprise.
submit_backtestThe monthly backtest quota: Pro 50, Enterprise unlimited.
submit_monte_carloThe separate Monte Carlo quota: Pro 20 runs a month and at most 50,000 paths; Enterprise unlimited runs and at most 100,000 paths. The selectable return processes also depend on the plan.
preview_constraintsEnterprise, the same entitlement that gates constraints at submission.
list_classification_mapsNone. A list saved while the plan allowed constraints stays readable afterwards; the gate sits on the submission.

Errors

A tool reports a refusal as a tool error whose text reaches the assistant. Four shapes exist:

  • A missing scope names the tool, the scopes it needs and the scopes the token has. Reconnect the connector and approve the scope.
  • A plan refusal names the capability and the plan, for example a constraints request on a plan without the constraints entitlement.
  • A refusal from the service is the HTTP status and its detail, in the form <status>: <detail>. A 404 means the id is not on this account; a 409 from cancel_job means the job had already finished.
  • An unexpected failure is reported only as Error calling tool '<name>'. The detail is withheld on purpose.
http
access denied: tool 'submit_backtest' requires scopes ['runs:write']; token has ['catalog:read', 'docs:read', 'runs:read']

409: <detail naming the state the job was already in>

Error calling tool 'get_job_result'

Some tools return a result object with an error field instead of a tool error, for example import_holdings when a file matches neither broker layout, and submit_optimization when a method name is not recognised, with the full list of valid names.

Links Back to the Web App

The result_url on a response opens the matching page. The page needs a sign-in to the same account that owns the run.

ObjectURL pattern
An optimization runhttps://www.foliolab.ai/results/{run_id}
A simulationhttps://www.foliolab.ai/results/{run_id}/monte-carlo?mc={mc_run_id}
A standalone backtesthttps://www.foliolab.ai/backtests/{backtest_run_id}
An inline rolling backtesthttps://www.foliolab.ai/results/{run_id}/rolling

Connection and Token Lifetimes

  • Discovery. A client finds the authorization server at /.well-known/oauth-authorization-server and the protected resource at /.well-known/oauth-protected-resource, which also answers under the resource path, for example /.well-known/oauth-protected-resource/mcp.
  • Client identity. A client either registers at POST /oauth/register or presents an HTTPS URL to a client ID metadata document as its client_id, which is how ChatGPT connects.
  • The flow. Authorization code with PKCE. Only the S256 challenge method is accepted. An authorization code is valid for 10 minutes.
  • Tokens. An access token is valid for 15 minutes. A refresh token is valid for 30 days and is replaced at every use.
  • Plan checks. The plan is checked when you approve the connection and again at every refresh. A plan that no longer carries MCP access makes the next refresh fail.
  • Revocation. Revoking a connector in account settings ends its refresh tokens at once, so the next refresh fails. An access token already issued stays valid until it expires, which is at most 15 minutes later.

What an Assistant Must Not Do

  • Present a Monte Carlo probability without its assumptions block. Probabilities are conditional on the selected model, the frozen optimizer-time inputs, the effective configuration, the engine version and the seed. No return generator has been validated out of sample, and none is a calibrated forecast.
  • Present a backtest as expected future performance, or a favourable backtest as evidence that a policy will outperform.
  • Resubmit an existing portfolio through submit_optimization to attach a backtest. That spends a second run and refits the weights; submit_backtest holds the parent's frozen inputs.

Not investment advice. Past performance is not indicative of future results.