-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
9af1625
commit 46c48aa
Showing
3 changed files
with
169 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,39 @@ | ||
name: Tests | ||
|
||
on: | ||
push: | ||
branches: [ main ] | ||
pull_request: | ||
branches: [ main ] | ||
workflow_dispatch: # Allows manual triggering | ||
|
||
jobs: | ||
test: | ||
runs-on: ubuntu-latest | ||
strategy: | ||
matrix: | ||
python-version: ["3.7", "3.8", "3.9", "3.10", "3.11"] | ||
|
||
steps: | ||
- uses: actions/checkout@v3 | ||
|
||
- name: Set up Python ${{ matrix.python-version }} | ||
uses: actions/setup-python@v4 | ||
with: | ||
python-version: ${{ matrix.python-version }} | ||
|
||
- name: Install dependencies | ||
run: | | ||
python -m pip install --upgrade pip | ||
pip install -e ".[test]" | ||
- name: Run tests | ||
run: | | ||
pytest | ||
- name: Upload coverage reports to Codecov | ||
uses: codecov/codecov-action@v3 | ||
with: | ||
file: ./coverage.xml | ||
flags: unittests | ||
fail_ci_if_error: true |
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,130 @@ | ||
import pytest | ||
from conditional_parser import ConditionalArgumentParser | ||
import sys | ||
|
||
|
||
def test_basic_functionality(): | ||
"""Test that basic ArgumentParser functionality works.""" | ||
parser = ConditionalArgumentParser() | ||
parser.add_argument("--flag", action="store_true") | ||
parser.add_argument("--value", type=int, default=42) | ||
|
||
args = parser.parse_args(["--flag", "--value", "123"]) | ||
assert args.flag is True | ||
assert args.value == 123 | ||
|
||
args = parser.parse_args([]) | ||
assert args.flag is False | ||
assert args.value == 42 | ||
|
||
|
||
def test_simple_conditional(): | ||
"""Test conditional argument with direct value matching.""" | ||
parser = ConditionalArgumentParser() | ||
parser.add_argument("--format", choices=["json", "csv"], default="json") | ||
parser.add_conditional("format", "csv", "--delimiter", default=",") | ||
|
||
# Test with CSV format | ||
args = parser.parse_args(["--format", "csv", "--delimiter", "|"]) | ||
assert args.format == "csv" | ||
assert args.delimiter == "|" | ||
|
||
# Test with JSON format (delimiter should not be available) | ||
args = parser.parse_args(["--format", "json"]) | ||
assert args.format == "json" | ||
assert not hasattr(args, "delimiter") | ||
|
||
# Test default CSV case | ||
args = parser.parse_args(["--format", "csv"]) | ||
assert args.delimiter == "," | ||
|
||
|
||
def test_callable_conditional(): | ||
"""Test conditional argument with callable condition.""" | ||
parser = ConditionalArgumentParser() | ||
parser.add_argument("--add_conditional", type=str, default="False") | ||
parser.add_conditional("add_conditional", lambda x: x.lower() == "true", "--extra-arg", action="store_true") | ||
|
||
# Test threshold above condition | ||
args = parser.parse_args(["--add_conditional", "True", "--extra-arg"]) | ||
assert args.extra_arg | ||
|
||
# Test threshold below condition (should raise error if trying to use conditional) | ||
with pytest.raises(SystemExit): | ||
parser.parse_args(["--add_conditional", "False", "--extra-arg"]) | ||
|
||
with pytest.raises(SystemExit): | ||
parser.parse_args(["--extra-arg"]) | ||
|
||
|
||
def test_hierarchical_conditionals(): | ||
"""Test nested conditional arguments.""" | ||
parser = ConditionalArgumentParser() | ||
parser.add_argument("--use-model", action="store_true") | ||
parser.add_conditional("use_model", True, "--model-type", choices=["cnn", "rnn"], required=True) | ||
parser.add_conditional("model_type", "cnn", "--kernel-size", type=int, default=3) | ||
parser.add_conditional("model_type", "rnn", "--hidden-size", type=int, default=128) | ||
|
||
# Test CNN path | ||
args = parser.parse_args(["--use-model", "--model-type", "cnn", "--kernel-size", "5"]) | ||
assert args.use_model is True | ||
assert args.model_type == "cnn" | ||
assert args.kernel_size == 5 | ||
|
||
args = parser.parse_args(["--use-model", "--model-type", "cnn"]) | ||
assert args.kernel_size == 3 | ||
assert not hasattr(args, "hidden_size") | ||
|
||
# Test RNN path (kernel-size should not be available) | ||
args = parser.parse_args(["--use-model", "--model-type", "rnn"]) | ||
assert args.model_type == "rnn" | ||
assert args.hidden_size == 128 | ||
assert not hasattr(args, "kernel_size") | ||
|
||
|
||
def test_required_conditionals(): | ||
"""Test behavior of required conditional arguments.""" | ||
parser = ConditionalArgumentParser() | ||
parser.add_argument("--use-auth", action="store_true") | ||
parser.add_conditional("use_auth", True, "--username", required=True) | ||
|
||
# Should fail without required conditional | ||
with pytest.raises(SystemExit): | ||
parser.parse_args(["--use-auth"]) | ||
|
||
# Should work with required conditional | ||
args = parser.parse_args(["--use-auth", "--username", "user123"]) | ||
assert args.username == "user123" | ||
|
||
|
||
def test_help_text(): | ||
"""Test that help text includes conditionals appropriately.""" | ||
parser = ConditionalArgumentParser() | ||
parser.add_argument("--mode", choices=["simple", "advanced"]) | ||
parser.add_conditional("mode", "advanced", "--extra-param") | ||
|
||
# Capture help output | ||
old_stdout = sys.stdout | ||
help_output = [] | ||
try: | ||
import io | ||
|
||
sys.stdout = io.StringIO() | ||
with pytest.raises(SystemExit): | ||
parser.parse_args(["--mode", "advanced", "--help"]) | ||
help_output = sys.stdout.getvalue() | ||
finally: | ||
sys.stdout = old_stdout | ||
|
||
assert "--mode" in help_output | ||
assert "--extra-param" in help_output | ||
|
||
|
||
def test_invalid_condition(): | ||
"""Test error handling for invalid conditions.""" | ||
parser = ConditionalArgumentParser() | ||
parser.add_argument("--value", type=int) | ||
|
||
# Test callable with wrong number of arguments | ||
with pytest.raises(ValueError): | ||
parser.add_conditional("value", lambda x, y: x > y, "--flag") |