Custom no-code evaluations
Custom no-code evaluations let you evaluate a specific dataset with an exact-match or multiple-choice scoring style without writing or maintaining custom evaluation code. Define the dataset, prompt template, scoring style, and optional model declaratively in the configuration file.
For highly specialized evaluations such as multi-step workflows, LLM judge-based evaluations, or agent evaluations, use a custom code evaluation instead.
Configuration reference
You can configure your custom_nocode evaluation with the following fields in your quantiles.toml or .quantiles.toml configuration file:
| Field | Type | Required | Description |
|---|---|---|---|
type | string | yes | Selects the no-code custom evaluation runner. Must be "custom_nocode". |
style | table | yes | Defines how responses are parsed and scored, along with the fields required by the selected scoring method. |
style.type | string | yes | Setting style.type = "exact_match" scores an open answer or label against a golden-answer column. Setting style.type = "multiple_choice" normalizes choices, extracts the selected label from the response, and scores it against a configured label, index, or correct-choice column. |
dataset | table | yes | Identifies the Hugging Face dataset to evaluate, including its optional subset, split, and revision. |
dataset.name | string | yes | Hugging Face dataset ID, such as "quantiles/simpleqa-verified". |
dataset.config_name | string | no | Dataset configuration or subset to load. If omitted, Quantiles infers the configuration. |
dataset.split | string | no | Dataset split to evaluate. If omitted, Quantiles prefers test, validation, eval, or train, in that order, then uses the first available split. |
dataset.revision | string | no | Dataset branch, tag, or commit to load. If omitted, Hugging Face uses the dataset’s default revision. |
model | string or table | no | Model or sampler used to generate responses. If omitted, Quantiles uses its built-in random demo sampler. See model configuration for provider-backed models. |
prompt_template_file | string | yes | Path to an existing Jinja prompt template. The template can access the complete dataset row and, for multiple-choice evaluations, normalized choices. |
style.golden_column | string | conditional | Dataset column containing the expected answer for exact-match scoring. Required when style.type = "exact_match". |
style.choices | table | conditional | Defines where multiple-choice options come from. Specify exactly one of style.choices.column or style.choices.columns. |
style.choices.column | string | conditional | Dataset column containing the choices as an ordered array or an object keyed by the configured choice labels. |
style.choices.columns | array of strings | conditional | Ordered list of dataset columns whose scalar values become the choices. Each column maps to the choice label at the same position. |
style.answer | table | conditional | Defines how Quantiles determines the correct multiple-choice option. Specify exactly one supported answer source. |
style.answer.label_column | string | conditional | Dataset column containing the correct choice label. Values are trimmed and matched case-insensitively against style.choice_labels. |
style.answer.index_column | string | conditional | Dataset column containing the numeric position of the correct choice before optional shuffling. |
style.answer.index_base | integer | no | Starting index used by style.answer.index_column, such as 0 for zero-based indexes or 1 for one-based indexes. Defaults to 0. |
style.answer.correct_choice_column | string | conditional | Name of the entry in style.choices.columns that always contains the correct answer. Only supported with column-backed choices. |
style.choice_labels | array of strings | conditional | Unique labels assigned to choices in order, such as ["A", "B", "C", "D"]. Required for multiple-choice evaluations. |
style.shuffle | table | no | Enables deterministic per-row shuffling of choices before labels are assigned. |
style.shuffle.seed_column | string | conditional | Dataset column containing a stable row-specific value used to reproduce the same shuffled order. Required when style.shuffle is configured. |
limit | integer | no | Maximum number of dataset rows to evaluate. Defaults to all available rows and must be greater than zero. |
max_workers | integer | no | Maximum number of dataset rows evaluated concurrently. If omitted, Quantiles uses its configured runtime default. |
Styles
Custom no-code evaluations have two different styles, defined in the style.type field:
exact_match: an evaluation that compares the model’s response with an expected answer.multiple_choice: an evaluation that extract and score the model’s selection from a pre-configured (in the dataset) set of choices.
The following is an example of an exact-match custom no-code evaluation:
# Example of a custom no-code evaluation called "my_custom_nocode_eval"
[benchmarks.my_custom_nocode_eval]
# Type must be set to "custom_nocode" or it will default to "built-in"
type = "custom_nocode"
# Style sets how responses are parsed and scored
style = { type = "exact_match", golden_column = "answer" }
# Identifies the Hugging Face dataset to evaluate
dataset = { name = "quantiles/my_custom_nocode_eval_data" }
# This example uses the built-in demo model.
# Specify a provider backed model (such as OpenAI or Anthropic)
# if you want to use a different model. This will require
# an API key OPENAI_API_KEY environment variable.
model = "random"
# Path to an existing Jinja prompt template.
prompt_template_file = "prompts/qa.txt"Run it with:
qt run my_custom_nocode_evalFor additional examples, see the sample custom_nocode configuration .
Note: The demo model is intended only to validate the evaluation workflow. When using
model="random",style.type = "exact_match"generates random text and will typically produce very low accuracy. Withstyle.type = "multiple_choice", it samples uniformly fromstyle.choice_labels, so accuracy will usually be higher.
Prompt template
The prompt template defines the full prompt sent to the model for each dataset row. Set the prompt_template_file value to the path of a Jinja -formatted template file. At runtime, Quantiles exposes the complete dataset row to the template as row and, for multiple-choice evaluations, exposes the normalized choices as choices.
Dataset
Choose or publish a Hugging Face dataset whose rows contain the fields needed to render your prompt and score the model’s response. The evaluation style determines which additional fields are required:
style = { type = "exact_match", ... }evaluations need a golden-answer columnstyle = { type = "multiple_choice", ... }evaluations need fields describing the choices and the correct answer
Prompt fields
Quantiles exposes the complete dataset row to the Jinja template as row, so the template can reference any field needed to build the prompt. For example, Question: {{ row.question }} reads the question field. You can also use bracket notation, such as {{ row["Question"] }}, for field names that cannot be accessed cleanly with dot notation.
Exact-match answer column
For style.type = "exact_match" evaluations, the style.golden_column field identifies the dataset field containing the expected response. The field must contain a string, number, or boolean, which Quantiles converts to text. Quantiles trims leading and trailing whitespace from the model response and expected response before comparing them; the comparison is otherwise case-sensitive.
Multiple-choice columns
For style.type = "multiple_choice", choices can come from one dataset field containing an array or label-keyed object, configured with style.choices.column, or from several scalar fields, configured with style.choices.columns. Quantiles assigns the configured labels to these choices and exposes the normalized { label, text } entries to the prompt template as choices.
Multiple-choice answer column
Multiple-choice evaluations can identify the correct choice through style.answer.label_column, which contains a configured choice label; style.answer.index_column, which contains a numeric index and supports an optional index_base; or style.answer.correct_choice_column, which names the choice field known to contain the correct answer.
Shuffle seed column
When choice shuffling is enabled, style.shuffle.seed_column identifies a dataset field containing a stable string, number, or boolean for each row. Quantiles uses this value to shuffle the row’s choices deterministically.
Prompt template
The prompt template defines the full prompt sent to the model for each dataset row. Set the prompt_template_file value to the path of a Jinja -formatted template file. At runtime, Quantiles exposes the complete dataset row to the template as row and, for multiple-choice evaluations, exposes the normalized choices as choices.
{{ row.question }}
{% for choice in choices %}
{{ choice.label }}. {{ choice.text }}
{% endfor %}Dataset
Choose or publish a Hugging Face dataset whose rows contain the fields needed to render your prompt and score the model’s response. The evaluation style determines which additional fields are required:
style = { type = "exact_match", ... }evaluations need a golden-answer columnstyle = { type = "multiple_choice", ... }evaluations need fields describing the choices and the correct answer
Prompt fields
Quantiles exposes the complete dataset row to the Jinja template as row, so the template can reference any field needed to build the prompt. For example, Question: {{ row.question }} reads the question field. You can also use bracket notation, such as {{ row["Question"] }}, for field names that cannot be accessed cleanly with dot notation.
Exact-match answer column
For style.type = "exact_match" evaluations, the style.golden_column field identifies the dataset field containing the expected response. The field must contain a string, number, or boolean, which Quantiles converts to text. Quantiles trims leading and trailing whitespace from the model response and expected response before comparing them; the comparison is otherwise case-sensitive.
Multiple-choice columns
For style.type = "multiple_choice", choices can come from one dataset field containing an array or label-keyed object, configured with style.choices.column, or from several scalar fields, configured with style.choices.columns. Quantiles assigns the configured labels to these choices and exposes the normalized { label, text } entries to the prompt template as choices.
Multiple-choice answer column
Multiple-choice evaluations can identify the correct choice through style.answer.label_column, which contains a configured choice label; style.answer.index_column, which contains a numeric index and supports an optional index_base; or style.answer.correct_choice_column, which names the choice field known to contain the correct answer.
Shuffle seed column
When choice shuffling is enabled, style.shuffle.seed_column identifies a dataset field containing a stable string, number, or boolean for each row. Quantiles uses this value to shuffle the row’s choices deterministically.
Metrics and results
Each custom_nocode sample emits the following metrics:
is_correctindicates whether the parsed response matches the expected answer.response_parsedindicates whether Quantiles could parse the response. Exact-match responses are always considered parsed; for multiple-choice evaluations, this value is0when the response cannot be parsed as a configured choice label.latency_msrecords the sample’s execution latency in milliseconds.
While each run emits these aggregate metrics:
accuracy,correct_count,incorrect_count, andtotal_countparsed_response_count,unparsed_response_count, andparse_ratemean_latency_ms,median_latency_ms,p95_latency_ms,p99_latency_ms,min_latency_ms, andmax_latency_ms
Opt-in aggregates for multiple_choice evaluations
Multiple-choice runs can also emit more aggregate metrics, if you opt-in to them. Use the metrics array in your evaluation’s configuration to do so.
For example, to enable F1 and related aggregates, specify the following:
metrics = ["f1"]This opt-in metric enables the following aggregates:
macro_precision,macro_recall, andmacro_f1- the arithmetic means of the raw, un-weighted precision, recall and F1 metrics for each label.weighted_precision,weighted_recall, andweighted_f1- the weighted average of the precision, recall and F1 metrics for each label. To compute the weight of each label, that label’s support (e.g. the number of samples whose expected answer is that label) is used.precision_label_N,recall_label_N, andf1_label_N- the evaluation of the labelNas the positive class against all other labels.support_label_N- the number of samples whose expected answer is that label, andNis the label’s index instyle.choice_labels.
Precision, recall, and F1 are reported as
0when their denominator is zero. The confusion matrix uses expected labels as rows and predicted labels, plus the unparsed bucket, as columns.
To enable a confusion matrix, specify the following:
metrics = ["confusion"]This opt-in metric shows a representation of a confusion matrix, with the following outputs:
confusion_matrix_G_P- the number of samples whose expected label has indexGand whose parsed prediction has indexP. These cells form the parsed-label columns of the run’s confusion matrix.confusion_matrix_G_unparsed- the number of samples whose expected label has indexGbut whose response could not be parsed as a configured label. These cells form the confusion matrix’s additional unparsed-prediction column.
The --json flag and opt-in aggregates
By default, if you specify a metric type like metrics = ["confusion"], that metric will only be computed and displayed if you pass the --json to your command (e.g. qt show --json). To compute and show the metric in all cases, regardless of whether the --json flag is passed, specify the metrics like the below:
metrics = [{name = "confusion", show = "all"}]Use coding agents to create custom no-code evaluations
Use the Quantiles agent skill to use coding agents to build, run and analyze custom no-code evaluations with the qt CLI. Before proceeding, install the skill. Then, customize the the below prompt to create a custom no-code evaluation:
Create a custom no-code evaluation in `quantiles.toml` using the <your HuggingFace dataset> dataset, the <prompt column> prompt column, the <answer column> golden answer column, and a prompt template file. Run 10 samples and summarize the results.See Agents Overview for more detail on using agents with Quantiles.