---
title: "Files and Batch API Workflows"
output: rmarkdown::html_vignette
vignette: >
  %\VignetteIndexEntry{Files and Batch API Workflows}
  %\VignetteEngine{knitr::rmarkdown}
  %\VignetteEncoding{UTF-8}
---

```{r setup, include = FALSE}
fixture_dir <- "files-batches"
recording <- nzchar(Sys.getenv("FOUNDRY_RECORD_DOCS"))
have_fixtures <- dir.exists(fixture_dir) && length(list.files(fixture_dir)) > 0
run_api <- requireNamespace("httptest2", quietly = TRUE) &&
  (recording || have_fixtures)

# Attach foundryR before start_vignette(): httptest2 only sources the package's
# inst/httptest2/start-vignette.R (which sets replay placeholders) from attached
# packages.
library(foundryR)

if (run_api) {
  httptest2::start_vignette(fixture_dir)
}

knitr::opts_chunk$set(
  collapse = TRUE,
  comment = "#>",
  eval = run_api
)
```

```{r libraries, eval = TRUE}
library(foundryR)
```

The Batch API is useful when your research task has hundreds or thousands of
independent rows: survey coding, abstract screening, entity extraction, document
classification, or large-scale summarization.

## Prepare JSONL locally

`foundry_batch_requests()` runs locally. It converts a data frame into the JSON
Lines shape expected by the Batch API.

```{r batch-jsonl, eval = TRUE}
survey <- data.frame(
  id = c("resp-001", "resp-002", "resp-003"),
  response = c(
    "The workshop was clear and practical.",
    "I liked the examples but wanted more time.",
    "The setup instructions were confusing."
  )
)

jsonl <- tempfile(fileext = ".jsonl")

request_file <- foundry_batch_requests(
  survey,
  input = "response",
  path = jsonl,
  model = "gpt-5-nano",
  custom_id = "id",
  body = list(
    instructions = "Classify the response sentiment as positive, neutral, or negative."
  )
)

request_file
head(readLines(jsonl), 2)
```

The example files use R's temporary directory and are removed after use. For
results you want to keep, choose an explicit output path in your own workflow.

## Upload and create a batch

Uploading and batch creation call the Foundry service, so these chunks are not
run while building the vignette.

```{r upload-create, eval = FALSE}
file <- foundry_file_upload(jsonl, purpose = "batch")
unlink(jsonl)

batch <- foundry_batch_create(
  input_file_id = file$file_id,
  endpoint = "/v1/responses"
)
```

The returned objects include service identifiers, status fields, file sizes,
completion windows, and request counts.

## Poll and download results

These service calls are not run during rendering. Poll until the batch status
is `"completed"` before downloading its output.

```{r poll-download, eval = FALSE}
batch <- foundry_batch_get(batch$batch_id)
output_path <- tempfile(fileext = ".jsonl")

foundry_file_download(
  file_id = batch$output_file_id,
  path = output_path
)
```

Output files are JSONL too. Read a few lines first before parsing a large job:

```{r output-shape, eval = FALSE}
output_lines <- readLines(output_path, n = 2)
head(output_lines)
unlink(output_path)
```

## Practical advice

- Start with 10 to 20 rows and inspect the output before scaling up.
- Use stable `custom_id` values so results join back to your data frame.
- Store prompts and schema versions with your analysis code for reproducibility.
- Download both output and error files when a batch finishes.

```{r cleanup, include = FALSE, eval = TRUE}
unlink(jsonl)
if (run_api) {
  httptest2::end_vignette()
}
```
