% Generated by roxygen2: do not edit by hand
% Please edit documentation in R/fd_run.R
\name{fd_run}
\alias{fd_run}
\title{Run the featdelta incremental feature pipeline}
\usage{
fd_run(
  con,
  sql,
  defs,
  key,
  feat_table_name,
  verbose = FALSE,
  fetch_mode = c("new_only", "all"),
  use_max_key = FALSE,
  fetch_limit = NULL,
  compute_strict = TRUE,
  compute_envir = NULL,
  create_table = "auto",
  alter_table = TRUE,
  update_table = TRUE,
  dialect = NULL,
  chunk_size = NULL,
  fail_fast = TRUE,
  return_data = c("none", "features", "raw", "both"),
  preview_n = 10L,
  ...
)
}
\arguments{
\item{con}{A live \code{DBI} connection.}

\item{sql}{SQL query used to fetch raw rows.}

\item{defs}{A \code{featdelta_defs} object created by \code{fd_define()}.}

\item{key}{Character scalar naming the key column shared by raw data and
feature table.}

\item{feat_table_name}{Character scalar naming the target feature table.}

\item{verbose}{Logical. If \code{TRUE}, print progress messages.}

\item{fetch_mode}{Fetch mode. \code{"new_only"} fetches rows whose key is not yet
present in \code{feat_table_name}. \code{"all"} fetches all rows returned by \code{sql},
allowing explicit refresh/backfill runs.}

\item{use_max_key}{Logical. Passed to \code{fd_fetch()} when \code{fetch_mode = "new_only"} and the feature table already exists.}

\item{fetch_limit}{Optional positive row limit applied after fetching. This
is intended for previews and small dry development runs, not as a SQL
optimizer.}

\item{compute_strict}{Logical strictness flag passed to \code{fd_compute()}.}

\item{compute_envir}{Optional environment override passed to \code{fd_compute()}.}

\item{create_table}{Logical or \code{"auto"}. Passed to \code{fd_upsert()}.}

\item{alter_table}{Logical. Passed to \code{fd_upsert()}.}

\item{update_table}{Logical. Passed to \code{fd_upsert()}.}

\item{dialect}{Optional dialect override. Supported values are \code{"postgres"},
\code{"sqlite"}, and \code{"mysql"}.}

\item{chunk_size}{Optional chunk size. Passed to \code{fd_upsert()}.}

\item{fail_fast}{Logical. If \code{TRUE}, stage errors are raised immediately. If
\code{FALSE}, errors from fetch, compute, or upsert are captured in the returned
\code{fd_run_report}.}

\item{return_data}{Controls whether raw and/or computed data should be
included in the returned run report.}

\item{preview_n}{Non-negative number of rows to include in report previews.}

\item{...}{Reserved for future context options passed to \code{resolve_ctx()}.}
}
\value{
An object of class \code{"fd_run_report"} containing stage summaries,
timings, row counts, the compute report, and the upsert report. Depending
on \code{return_data}, it may also contain raw and/or computed feature data.
}
\description{
Executes the standard featdelta pipeline:
}
\details{
\code{fd_fetch()} -> \code{fd_compute()} -> \code{fd_upsert()}

\code{fd_run()} is the orchestration entry point that connects database fetching,
in-memory computation, and database upsert into a single incremental run.

\code{fetch_mode = "new_only"} is the default incremental mode. If the feature
table already exists, \code{fd_fetch()} returns only rows whose key is missing
from the feature table. If the feature table does not exist yet, all rows
returned by \code{sql} are fetched because no rows have been processed. This mode
is key-based: it does not recompute existing feature-table rows just because
feature definitions changed or new feature definitions were added.

\code{fetch_mode = "all"} is an explicit refresh/backfill mode. It recomputes all
rows returned by \code{sql} and passes them to \code{fd_upsert()}. With the default
\code{update_table = TRUE}, existing keys are updated and new keys are inserted.
Use this mode when existing feature values should be refreshed, for example
after changing a definition or adding a feature that should be backfilled for
already-processed keys.

\code{fd_run()} does not currently coordinate concurrent writers. For the MVP,
avoid running multiple \code{fd_run()}/\code{fd_upsert()} calls against the same feature
table at the same time. Concurrent writes to different feature tables are
independent.

The returned upsert report can include \code{extra_columns}: columns that exist in
the target feature table but are not produced by the current definitions.
These columns are left untouched; the package does not drop, rename, or retire
columns automatically.
}
\examples{
if (requireNamespace("RSQLite", quietly = TRUE)) {
con <- DBI::dbConnect(RSQLite::SQLite(), ":memory:")
on.exit(DBI::dbDisconnect(con), add = TRUE)

raw_cars <- mtcars
raw_cars$id <- seq_len(nrow(raw_cars))
DBI::dbWriteTable(con, "raw_cars", raw_cars)

defs <- fd_define(
  hp_per_cyl = hp / cyl,
  engine_ratios = fd_block({
    data.frame(
      disp_per_cyl = disp / cyl,
      wt_per_hp = wt / hp
    )
  })
)

res <- fd_run(
  con = con,
  sql = "SELECT * FROM raw_cars",
  defs = defs,
  key = "id",
  feat_table_name = "features",
  verbose = FALSE
)
res$success
}

}
\concept{featdelta pipeline helpers}
