đĨī¸ CLI & Argument Parsing â How the Program Accepts Input¶
What this doc covers: What
argparseis, why it exists, how it works in this project, and how the three arguments (--functions_definition,--input,--output) map to the program's execution flow.
Table of Contents¶
- What is argparse?
- Why Not Hardcode the Paths?
- How argparse Works
- The Three Arguments in This Project
- Default Values
- How Arguments Flow Through the Program
- Running the Program
What is argparse?¶
argparse is Python's standard library module for parsing command-line arguments. It lets your program accept input from the terminal when it's launched, instead of having paths or settings hardcoded inside the code.
uv run python -m src --input data/input/tests.json
â
argparse reads this
It handles three things automatically:
- Parsing the arguments the user passes
- Providing default values when arguments are omitted
- Generating a --help message that describes the program
Why Not Hardcode the Paths?¶
You could write this inside your code:
# Hardcoded â bad
fn_defs = load_function_definitions("data/input/functions_definition.json")
prompts = load_test_prompts("data/input/function_calling_tests.json")
This works locally, but it breaks the moment someone wants to run the program with different files â which is exactly what the peer reviewer will do. The subject explicitly states:
"The given input files may change during the peer review. Do not hardcode solutions based on the provided examples."
With argparse, the paths come from the command line â the reviewer can pass any files they want without touching your code.
How argparse Works¶
The basic pattern is always the same:
import argparse
def parse_args() -> argparse.Namespace:
parser = argparse.ArgumentParser(description="...")
parser.add_argument(
"--argument-name",
type=str,
default="default/value",
help="What this argument does"
)
return parser.parse_args()
Then in main():
def main() -> None:
args = parse_args()
print(args.argument_name) # access with dot notation
Key parameters of add_argument¶
| Parameter | Purpose | Example |
|---|---|---|
"--name" |
The flag name (with --) |
"--input" |
type |
Converts the string value to a Python type | type=str |
default |
Value used when the argument is not passed | default="data/input/tests.json" |
help |
Description shown in --help output |
help="Path to input file" |
Accessing values¶
After parse_args(), you access arguments with dot notation. Dashes in argument names become underscores:
--functions_definition â args.functions_definition
--input â args.input
--output â args.output
The Three Arguments in This Project¶
The subject specifies exactly how the program must be called:
uv run python -m src \
--functions_definition data/input/functions_definition.json \
--input data/input/function_calling_tests.json \
--output data/output/function_calling_results.json
This means three arguments are needed:
--functions_definition¶
The path to the JSON file that defines the available functions and their schemas.
Default: data/input/functions_definition.json
Used by: load_function_definitions() in data_loader.py
--input¶
The path to the JSON file containing the natural language prompts to process.
Default: data/input/function_calling_tests.json
Used by: load_test_prompts() in data_loader.py
--output¶
The path where the program writes the generated function calls JSON file.
Default: data/output/function_calling_results.json
Used by: the output writing logic in __main__.py
Default Values¶
The subject says:
"By default, the program will read input files from the
data/input/directory and write output to thedata/output/directory."
This means all three arguments are optional â if the user runs the program without any flags, it falls back to the default paths and still works correctly:
uv run python -m src # uses all defaults â
uv run python -m src --input other.json # overrides just --input â
This is exactly what default= in add_argument provides.
How Arguments Flow Through the Program¶
Command line:
uv run python -m src --input data/input/tests.json
â
parse_args()
returns args.input = "data/input/tests.json"
â
main(args)
â
load_test_prompts(args.input) â data_loader.py
load_function_definitions(args.functions_definition)
â
constrained_decoder
â
write output to args.output
The arguments are read once at startup and passed through to the functions that need them. Nothing inside data_loader.py, llm_engine.py, or constrained_decoder.py reads from sys.argv directly â they all receive paths as regular function parameters.
Running the Program¶
With all defaults¶
uv run python -m src
With custom paths¶
uv run python -m src \
--functions_definition data/input/functions_definition.json \
--input data/input/function_calling_tests.json \
--output data/output/function_calling_results.json
Via the Makefile¶
make run
The Makefile already has the default paths configured:
FUNCTIONS = data/input/functions_definition.json
INPUT = data/input/function_calling_tests.json
OUTPUT = data/output/function_calling_results.json
run:
uv run python -m src \
--functions_definition $(FUNCTIONS) \
--input $(INPUT) \
--output $(OUTPUT)
Getting help¶
uv run python -m src --help
argparse generates this automatically from the help= strings you provide in each add_argument call.
See also: UV_GUIDE.md for how uv run works with the project environment.
Official argparse docs: docs.python.org/3/library/argparse.html