Skip to content

chore: sweep codeql findings and fix - #505

Merged
mckornfield merged 15 commits into
mainfrom
codeql-findings-sweep/mck
May 26, 2026
Merged

chore: sweep codeql findings and fix#505
mckornfield merged 15 commits into
mainfrom
codeql-findings-sweep/mck

Conversation

@mckornfield

@mckornfield mckornfield commented May 21, 2026

Copy link
Copy Markdown
Collaborator

closes #18

  • make format && make check or via prek validation.
  • make test passes locally
  • make test-e2e passes locally
  • make test-ci-container passes locally (recommended)
  • GPU CI status check passes -- comment /sync on this PR to trigger a run (auto-triggers on ready-for-review)

Pre-Merge Checklist

  • New or updated tests for any fix or new behavior
  • Updated documentation for new features and behaviors, including docstrings for API docs.

Other Notes

  • Closes #

Summary by CodeRabbit

Release Notes

  • Bug Fixes

    • Improved error handling and exception propagation across data processing components for more reliable failure diagnostics.
    • Enhanced validation of iterable parsing in template rendering to prevent undefined states.
    • Strengthened numeric type conversions with explicit fallbacks for edge cases.
  • Refactor

    • Optimized data structure initialization and control flow for better performance.
    • Refined generator termination and return statements across utilities.
  • Tests

    • Updated test infrastructure for improved module import handling and test execution consistency.

Review Change Stack

@mckornfield
mckornfield requested review from a team as code owners May 21, 2026 16:50
@coderabbitai

coderabbitai Bot commented May 21, 2026

Copy link
Copy Markdown
Contributor

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: 91373ea4-f6d7-4b8d-83b6-56b66db5374a

📥 Commits

Reviewing files that changed from the base of the PR and between b99c1c7 and f8ec9f7.

📒 Files selected for processing (3)
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
💤 Files with no reviewable changes (3)
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
📜 Recent review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (4)
  • GitHub Check: Unit Tests (3.11)
  • GitHub Check: Unit Tests (3.12)
  • GitHub Check: Unit Tests (3.13)
  • GitHub Check: Smoke Tests

Walkthrough

This PR systematizes Python code quality across 40+ files: standardizing re.Pattern type references, removing unused imports, adding explicit control-flow returns and exhaustiveness markers, narrowing exception handlers to specific types, restructuring record initialization for eager unpacking, improving test isolation via dynamic imports, and refactoring callback logic for clearer error handling.

Changes

Code quality improvements: type annotations, imports, and error handling

Layer / File(s) Summary
Standardize re.Pattern type annotations across NER modules
src/nemo_safe_synthesizer/pii_replacer/ner/custom.py, src/nemo_safe_synthesizer/pii_replacer/ner/labels.py, src/nemo_safe_synthesizer/pii_replacer/ner/model.py, src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
Removes from re import Pattern imports and updates type annotations to reference re.Pattern directly; CustomRegexPattern now uses isinstance(self.regex, re.Pattern) instead of checking the string name.
Import cleanup and forward reference removal
src/nemo_safe_synthesizer/cli/artifact_structure.py, src/nemo_safe_synthesizer/cli/run.py, src/nemo_safe_synthesizer/config/replace_pii.py, src/nemo_safe_synthesizer/configurator/parameter.py, src/nemo_safe_synthesizer/configurator/parameters.py, src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
Removes unused get_logger imports, simplifies PathLike import to direct from os import PathLike, removes unused ParameterT TypeVar, and replaces quoted forward references with direct type annotations in function parameters.
Explicit returns, exhaustiveness markers, and control-flow clarity
src/nemo_safe_synthesizer/data_processing/actions/dates.py, src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py, src/nemo_safe_synthesizer/data_processing/records/json_record.py, src/nemo_safe_synthesizer/training/callbacks.py, tests/conftest.py
Replaces implicit None returns and no-op pass statements with explicit return, continue, and return None; adds AssertionError("unreachable") after exhaustive pattern matches to enforce completeness.
Exception handling improvements and error path clarification
src/nemo_safe_synthesizer/data_processing/dataset.py, src/nemo_safe_synthesizer/data_processing/actions/dates.py, src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py, src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py, src/nemo_safe_synthesizer/evaluation/statistics/stats.py, src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py, src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py, src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py, src/nemo_safe_synthesizer/generation/vllm_backend.py
Narrows exception catches from broad Exception to specific types (TypeError, ValueError, OverflowError); adds value normalization (str conversion, empty dict/array) in error paths; improves failure logging with exc_info=True; ensures deterministic outcomes on conversion failures.
Record initialization and unpacking lifecycle changes
src/nemo_safe_synthesizer/data_processing/records/base.py, src/nemo_safe_synthesizer/data_processing/records/json_record.py
BaseRecord.__init__ no longer calls self.unpack(); JSONRecord gains explicit __init__ that eagerly unpacks JSON via new _unpack_json() helper; unpack() refactored to reset state and delegate; explicit return None added for path lookups.
Evaluation callback refactoring and NER config parsing
src/nemo_safe_synthesizer/training/callbacks.py, src/nemo_safe_synthesizer/pii_replacer/ner/custom.py, src/nemo_safe_synthesizer/pii_replacer/ner/models.py
InferenceEvalCallback.on_evaluate refactored to dispatch on GenerationStatus and log training incompleteness markers; NER config parsers return empty lists deterministically instead of None; CacheManager.resolve simplified to direct obj_from_fs call.
Code-style improvements: lambda simplification, timing fix, file I/O
src/nemo_safe_synthesizer/config/autoconfig.py, src/nemo_safe_synthesizer/data_processing/actions/data_actions.py, src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py, tools/codestyle/copyright_fixer.py
Simplifies lambda expressions in pandas apply calls; removes redundant timing-log updates; improves file I/O with context-managed open(); imports suppress for selective exception handling.

Test module import isolation and callback testing

Layer / File(s) Summary
Dynamic module imports in test files for better isolation
tests/e2e/test_dataset_config.py, tests/e2e/test_safe_synthesizer.py, tests/generation/test_batch.py, tests/generation/test_vllm_backend.py, tests/observability/test_observability.py, tests/preflight/test_plugin_registration.py, tests/telemetry/test_telemetry.py
Test modules now use importlib.import_module() to load submodules at runtime rather than module-import time, enabling controlled side-effect handling and reliable mock patching; removes module-level VllmBackend import to prevent initialization side effects.
Training callback test helper and terminal status verification
tests/training/test_callbacks.py
Refactors _invoke_on_evaluate helper to return (state, control) tuple for test assertions; adds TestInferenceEvalCallbackTerminalStatus class to verify terminal generation behavior when processor yields no records.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes


Suggested reviewers

  • kendrickb-nvidia
  • binaryaaron
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 69.12% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'chore: sweep codeql findings and fix' directly describes the main objective of addressing CodeQL security findings, which is the primary focus of the PR.
Linked Issues check ✅ Passed The PR addresses issue #18's requirement to review and triage CodeQL findings by implementing fixes across multiple modules to resolve the identified security issues.
Out of Scope Changes check ✅ Passed Changes span multiple modules but are all focused on addressing CodeQL findings: improving type annotations, error handling, control flow, and import practices—all within the scope of security-focused code improvements.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codeql-findings-sweep/mck

Comment @coderabbitai help to get the list of available commands and usage tips.

Comment thread src/nemo_safe_synthesizer/cli/artifact_structure.py Dismissed
Comment thread src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py Fixed
Comment thread src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py Fixed
@coderabbitai coderabbitai Bot added test Test-only addition or change chore Maintenance not tied to a user-visible change refactor Internal restructuring with no behavior change labels May 21, 2026

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1


ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: 60b16746-245b-49c1-906b-716056e459db

📥 Commits

Reviewing files that changed from the base of the PR and between 0bab4f3 and cc94b51.

📒 Files selected for processing (38)
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/config/replace_pii.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/configurator/parameters.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/data_processing/records/base.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • tests/cli/test_run.py
  • tests/conftest.py
  • tests/e2e/test_dataset_config.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/generation/test_batch.py
  • tests/generation/test_vllm_backend.py
  • tests/observability/test_observability.py
  • tests/preflight/test_plugin_registration.py
  • tests/telemetry/test_telemetry.py
  • tools/codestyle/copyright_fixer.py
💤 Files with no reviewable changes (4)
  • src/nemo_safe_synthesizer/config/replace_pii.py
  • src/nemo_safe_synthesizer/configurator/parameters.py
  • tests/generation/test_vllm_backend.py
  • src/nemo_safe_synthesizer/data_processing/records/base.py
📜 Review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (4)
  • GitHub Check: Unit Tests (3.12)
  • GitHub Check: Unit Tests (3.11)
  • GitHub Check: Unit Tests (3.13)
  • GitHub Check: Smoke Tests
🧰 Additional context used
📓 Path-based instructions (18)
**/*.{md,markdown,py}

📄 CodeRabbit inference engine (.cursor/rules/agent-markdown-style.mdc)

**/*.{md,markdown,py}: Avoid decorative bold (**text**) in list items, body text, and docstrings; use structural cues (headers, list markers, colons, backticks) for emphasis instead
Use backticks for code identifiers, paths, and CLI commands in markdown and docstrings

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • tests/cli/test_run.py
  • tools/codestyle/copyright_fixer.py
  • tests/e2e/test_safe_synthesizer.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • tests/conftest.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • tests/preflight/test_plugin_registration.py
  • src/nemo_safe_synthesizer/observability.py
**/*.py

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

**/*.py: Use American English spelling: 'initialize' not 'initialise', 'recognize' not 'recognise', 'color' not 'colour'.
Use observability.get_logger(__name__) for logging, never logging.getLogger() or structlog.get_logger() directly.
Use category loggers: .runtime for internals, .user for progress/results, .system for system events.
Never use print() for operational output. Use click.echo() for CLI output or sys.stdout.write() for raw output in tools.
Use extra={} in logging for structured data that downstream tools should query or aggregate; use f-strings for human-readable context.
Raise from the custom error hierarchy with dual inheritance: SafeSynthesizerError (base), UserError, DataError, ParameterError, GenerationError, InternalError.
Use NSSBaseModel for config/parameter models in config/ which define user-facing configuration. Use raw BaseModel or module-specific bases for data transfer objects and internal structures.
Use BaseSettings for env/CLI settings. Prefer AliasChoices on individual fields when a field needs to respond to both its Python name and an env var name.
Include Field(description=...) for Pydantic model fields as the canonical field docstring for API documentation and CLI help text.
Use assignment-style type = Field(default=..., description="...") as the default for Pydantic model fields because type checkers understand default, default_factory, and alias in assignment style.
Use Annotated only when the field carries additional metadata beyond Field() -- ValueValidator, AutoParam, DependsOnValidator, reusable constrained type aliases, nested-type constraints, or discriminated unions.
Put defaults as bare assignment (= value), not inside Field(default=...), when using Annotated. Exception: use assignment-style Field(default_factory=...) for defaults that cannot be expressed as bare assignments.
Use @dataclass(frozen=True) for immutable value objects and validators; mu...

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • tests/cli/test_run.py
  • tools/codestyle/copyright_fixer.py
  • tests/e2e/test_safe_synthesizer.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • tests/conftest.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • tests/preflight/test_plugin_registration.py
  • src/nemo_safe_synthesizer/observability.py
src/**/*.py

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

src/**/*.py: Use relative imports in src/ (e.g., from ..observability import get_logger).
Do not use print() statements in library code. Use get_logger(__name__) from observability.py or click.echo() for CLI.
Do not use assert for validation in library code. Use if/raise for input validation. assert statements can be stripped by -O and must never guard correctness.

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • src/nemo_safe_synthesizer/observability.py

⚙️ CodeRabbit configuration file

Review library code against STYLE_GUIDE.md. Focus on behavior, API contracts, error handling, resource cleanup, typing, logging, and user-facing failures. Public APIs and nontrivial functions need Google-style docstrings.

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • src/nemo_safe_synthesizer/observability.py
**/*.{py,sh,yaml,yml}

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

Include SPDX copyright header at the top: # SPDX-FileCopyrightText: Copyright (c) 2025-2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved. and # SPDX-License-Identifier: Apache-2.0. The make format command handles this automatically.

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • tests/cli/test_run.py
  • tools/codestyle/copyright_fixer.py
  • tests/e2e/test_safe_synthesizer.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • tests/conftest.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • tests/preflight/test_plugin_registration.py
  • src/nemo_safe_synthesizer/observability.py
**/*

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

**/*: Include a newline at the end of all files, never trailing whitespace. This is enforced by pre-commit.
Use line length of 120 characters for code, comments, and docstrings (configured in ruff.toml).

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • tests/cli/test_run.py
  • tools/codestyle/copyright_fixer.py
  • tests/e2e/test_safe_synthesizer.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • tests/conftest.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • tests/preflight/test_plugin_registration.py
  • src/nemo_safe_synthesizer/observability.py

⚙️ CodeRabbit configuration file

**/*: Review as a senior maintainer for NeMo Safe Synthesizer. Prioritize issues that can change behavior, break user workflows, weaken privacy guarantees, hide failures, make tests unreliable, or create maintenance risk. Avoid generic style commentary unless it points to a concrete project convention that automated tools will not catch.
Comment only when the finding is actionable and tied to changed code. For each finding, state the impact, the condition that triggers it, and the smallest practical fix. Prefer one precise comment over broad advice. Do not ask for refactors outside the PR scope unless the changed code creates the problem.
Review type guidance: - Potential issue: use for correctness bugs, data loss, privacy leaks,
security risks, broken public APIs, invalid config behavior, missing
validation, hidden failures, nondeterministic tests, or CI breakage.

  • Refactor suggestion: use for local maintainability problems introduced
    by the diff when they have clear future cost, such as duplicated setup,
    unclear boundaries, over-mocking, avoidable complexity, or opaque test
    helpers.
  • Nitpick: avoid in chill mode. Do not emit formatting, import-order,
    wording, or style-only comments unless automated tools cannot catch the
    issue and it affects maintainability.

Severity guidance: - Critical: security/privacy leaks, data loss, training/test/holdout
contamination, or broken release/package/core pipeline execution.

  • Major: incorrect generation/training/evaluation behavior, broken
    CLI/SDK public API, invalid config defaults or validators, or GPU/vLLM
    cleanup and process-isolation bugs likely to fail CI or production
    runs.
  • Minor: localized bugs, missing focused tests for changed behavior, or
    bad test patterns that weaken regression coverage.
  • Trivial: small cleanup with no behavior impact. Usually suppress in
    chill mode.
  • Info: context only. Avoid unless it helps reviewers understand risk.
    Safe-Synthesizer-specific review focus: - Data ...

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • tests/cli/test_run.py
  • tools/codestyle/copyright_fixer.py
  • tests/e2e/test_safe_synthesizer.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • tests/conftest.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • tests/preflight/test_plugin_registration.py
  • src/nemo_safe_synthesizer/observability.py
src/nemo_safe_synthesizer/pii_replacer/**/*.py

⚙️ CodeRabbit configuration file

Treat PII replacement changes as high-risk. Check entity coverage, replacement determinism, leakage of original values, handling of empty or multilingual text, and compatibility with optional dependencies.

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
src/nemo_safe_synthesizer/privacy/**/*.py

⚙️ CodeRabbit configuration file

Treat privacy changes as high-risk. Check DP accounting, parameter validation, data leakage, seed handling, model state persistence, and whether privacy guarantees are documented accurately.

Files:

  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
src/nemo_safe_synthesizer/configurator/**/*.py

⚙️ CodeRabbit configuration file

Review Pydantic-to-Click mapping carefully. Check option names, type conversion, nullable sub-config behavior, validation errors, help text, and compatibility with parse_overrides().

Files:

  • src/nemo_safe_synthesizer/configurator/parameter.py
tests/**

📄 CodeRabbit inference engine (.cursor/rules/repo-navigation.mdc)

Tests should mirror the src/ directory structure in tests/

Files:

  • tests/cli/test_run.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/conftest.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • tests/telemetry/test_telemetry.py
  • tests/e2e/test_dataset_config.py
  • tests/preflight/test_plugin_registration.py
tests/**/*.py

📄 CodeRabbit inference engine (.cursor/rules/repo-navigation.mdc)

Tests in tests/e2e/ should be auto-marked with e2e marker, tests in tests/smoke/ with smoke marker, others with unit marker

tests/**/*.py: Use absolute imports in tests/ (e.g., from nemo_safe_synthesizer.observability import get_logger).
Use fixture_ prefix convention for fixtures for grep-ability and to separate fixtures from test functions. Add a one-line docstring describing the fixture's purpose and data.
Use function-scoped fixtures by default. Session scope only when empirically justified by test runtime.
Use bare assert as the primary assertion style; pytest.raises() with match= for exceptions; pytest.approx() for floating-point comparisons.
Mark CUDA-dependent tests with @pytest.mark.e2e, @pytest.mark.smoke, or @pytest.mark.requires_gpu.
Mock only external boundaries, not internal implementation details.
Ensure test isolation: no shared mutable state or execution-order dependencies between tests. If something must be run first before executing a test, include it in the test or a fixture.
Use @pytest.mark.parametrize for testing multiple input combinations rather than copy-pasting similar tests.

Organize tests using pytest following the structure in tests/TESTING.md with support for unit tests, smoke tests, and end-to-end tests

Files:

  • tests/cli/test_run.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/conftest.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • tests/telemetry/test_telemetry.py
  • tests/e2e/test_dataset_config.py
  • tests/preflight/test_plugin_registration.py

⚙️ CodeRabbit configuration file

Review tests against tests/TESTING.md. Check marker usage, fixture naming, tmp_path usage, determinism, and GPU/vLLM process-isolation requirements. Flag slop tests that only check that code runs, assert result is not None when stronger invariants exist, over-mock internal implementation details, patch around the bug instead of reproducing it, or add broad snapshot/golden churn without a clear contract. Flag change detector tests that fail on harmless refactors, formatting, record ordering, incidental wording, or private implementation details without demonstrating a behavior regression. Prefer existing fixtures or focused new fixtures for repeated setup; keep tests DRY when reasonable without making the behavior under test opaque. print() is allowed in tests.

Files:

  • tests/cli/test_run.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/conftest.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • tests/telemetry/test_telemetry.py
  • tests/e2e/test_dataset_config.py
  • tests/preflight/test_plugin_registration.py
**/*test*.py

📄 CodeRabbit inference engine (AGENTS.md)

The unit_test marker is deprecated; use unit instead

Files:

  • tests/cli/test_run.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/conftest.py
  • tests/generation/test_batch.py
  • tests/observability/test_observability.py
  • tests/telemetry/test_telemetry.py
  • tests/e2e/test_dataset_config.py
  • tests/preflight/test_plugin_registration.py
tools/**

⚙️ CodeRabbit configuration file

Review tools as developer and CI infrastructure. Check that scripts use uv or Makefile wrappers instead of ad hoc python/pip commands, preserve read-only behavior for check targets, fail with clear messages, avoid hidden network or filesystem side effects, and stay consistent with STYLE_GUIDE.md and CONTRIBUTING.md. Tooling may use print() when it is a standalone script or intentional CLI output.

Files:

  • tools/codestyle/copyright_fixer.py
tools/codestyle/**

⚙️ CodeRabbit configuration file

Treat codestyle wrappers as CI-critical. Check consistency with Makefile targets, ruff.toml, ty configuration, copyright handling, staged-file behavior, read-only check modes, and whether fixes mutate only expected files.

Files:

  • tools/codestyle/copyright_fixer.py
src/nemo_safe_synthesizer/evaluation/**/*.py

⚙️ CodeRabbit configuration file

Treat evaluation changes as correctness-sensitive. Check metric inputs, holdout usage, privacy metric semantics, report data shape, missing-data handling, and whether unavailable metrics fail or degrade intentionally.

Files:

  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
src/nemo_safe_synthesizer/data_processing/**/*.py

⚙️ CodeRabbit configuration file

Review for data-contract regressions. Check input/training/test/synthetic naming, group boundaries, token-budget math, record ordering, schema and column validation, nullable dtypes, and deterministic behavior.

Files:

  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
tests/conftest.py

📄 CodeRabbit inference engine (.cursor/rules/repo-navigation.mdc)

Shared test fixtures should be defined in tests/conftest.py

Refer to tests/conftest.py for root-level auto-marking logic, load_test_dataset/load_test_dataframe helpers, and fixture_mock_processor pattern.

Files:

  • tests/conftest.py
src/nemo_safe_synthesizer/generation/**/*.py

⚙️ CodeRabbit configuration file

Review generation changes for retry loops, stopping conditions, invalid record handling, regex/structured output contracts, backend teardown, memory cleanup, and vLLM assumptions.

Files:

  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
src/nemo_safe_synthesizer/training/**/*.py

⚙️ CodeRabbit configuration file

Review training changes for dataset preprocessing, model path handling, artifact writes, LoRA/DP behavior, GPU memory usage, reproducibility, and cleanup on failure.

Files:

  • src/nemo_safe_synthesizer/training/callbacks.py
🪛 Ruff (0.15.13)
src/nemo_safe_synthesizer/evaluation/statistics/stats.py

[warning] 153-153: Do not catch blind exception: Exception

(BLE001)

src/nemo_safe_synthesizer/data_processing/dataset.py

[warning] 78-78: Do not catch blind exception: Exception

(BLE001)

🔇 Additional comments (38)
src/nemo_safe_synthesizer/data_processing/records/json_record.py (1)

109-125: LGTM!

Also applies to: 131-131, 138-138

tests/cli/test_run.py (1)

6-6: LGTM!

Also applies to: 21-22

tests/e2e/test_dataset_config.py (1)

5-5: LGTM!

Also applies to: 22-22

tests/e2e/test_safe_synthesizer.py (1)

13-13: LGTM!

Also applies to: 30-30

tests/generation/test_batch.py (1)

4-4: LGTM!

Also applies to: 17-18, 204-204

tests/observability/test_observability.py (1)

5-5: LGTM!

Also applies to: 36-37, 825-827, 831-831

tests/preflight/test_plugin_registration.py (1)

8-8: LGTM!

Also applies to: 35-36

tests/telemetry/test_telemetry.py (1)

5-5: LGTM!

Also applies to: 28-29

src/nemo_safe_synthesizer/pii_replacer/ner/models.py (1)

198-198: LGTM!

tools/codestyle/copyright_fixer.py (1)

202-203: LGTM!

src/nemo_safe_synthesizer/pii_replacer/ner/custom.py (3)

84-85: LGTM!


149-149: LGTM!


187-187: LGTM!

src/nemo_safe_synthesizer/pii_replacer/ner/labels.py (1)

33-33: LGTM!

Also applies to: 82-82

src/nemo_safe_synthesizer/pii_replacer/ner/model.py (1)

74-74: LGTM!

src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py (1)

48-48: LGTM!

Also applies to: 65-65

src/nemo_safe_synthesizer/cli/artifact_structure.py (2)

26-26: LGTM!

Also applies to: 235-235


82-82: LGTM!

Also applies to: 174-174, 232-232, 293-293

src/nemo_safe_synthesizer/configurator/parameter.py (1)

98-98: LGTM!

src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py (2)

22-22: LGTM!

Also applies to: 56-59


621-621: LGTM!

src/nemo_safe_synthesizer/cli/run.py (1)

208-213: LGTM!

src/nemo_safe_synthesizer/generation/regex_manager.py (1)

290-290: LGTM!

Also applies to: 323-323

src/nemo_safe_synthesizer/generation/vllm_backend.py (1)

102-102: LGTM!

Also applies to: 188-188, 314-314, 451-452, 456-456

src/nemo_safe_synthesizer/llm/metadata.py (1)

168-168: LGTM!

src/nemo_safe_synthesizer/observability.py (1)

150-150: LGTM!

Also applies to: 152-152, 165-165

src/nemo_safe_synthesizer/sdk/config_builder.py (1)

129-129: LGTM!

src/nemo_safe_synthesizer/data_processing/actions/dates.py (1)

373-373: LGTM!

Also applies to: 396-396, 436-436

src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py (1)

253-253: LGTM!

Also applies to: 442-446

src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py (1)

317-317: LGTM!

src/nemo_safe_synthesizer/training/callbacks.py (1)

333-333: LGTM!

tests/conftest.py (1)

267-267: LGTM!

src/nemo_safe_synthesizer/data_processing/dataset.py (1)

12-13: LGTM!

Also applies to: 67-73, 79-80

src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py (1)

195-195: LGTM!

src/nemo_safe_synthesizer/evaluation/statistics/stats.py (1)

148-148: LGTM!

Also applies to: 154-154

src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py (1)

271-275: LGTM!

src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py (1)

128-129: LGTM!

src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py (1)

314-314: LGTM!

Comment thread src/nemo_safe_synthesizer/training/callbacks.py
@coderabbitai coderabbitai Bot added bug Defects in shipped behavior and removed test Test-only addition or change chore Maintenance not tied to a user-visible change refactor Internal restructuring with no behavior change labels May 21, 2026
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
@greptile-apps

greptile-apps Bot commented May 21, 2026

Copy link
Copy Markdown
Contributor

Greptile Summary

This PR sweeps CodeQL findings across the codebase, tightening exception handling, fixing implicit None returns, and clarifying control flow. It also refactors JSONRecord to unpack data at construction time and replaces a chain-of-responsibility loop in CacheManager with a direct method call.

  • Exception handling: Bare except Exception: pass blocks are narrowed to specific exception types; several now assign an explicit fallback value (str(value), [], or an empty array) instead of silently falling through, making failure paths predictable.
  • Control flow / return paths: BaseRecord.__init__ no longer calls unpack(); JSONRecord compensates by overriding __init__ and preserving a public unpack() method. InferenceEvalCallback uses continue/break instead of the was_stopped flag, correctly exiting the generation loop on the first terminal status.
  • Code hygiene: from re import Pattern is replaced with re.Pattern everywhere, unused ParameterT TypeVar and logger instances are removed, and tests switch to importlib.import_module for module-level patching.

Confidence Score: 5/5

Safe to merge — the changes are mechanical cleanups with no logic regressions found.

Every changed code path was reviewed: exception narrowing is appropriate for the APIs in question, the JSONRecord construction refactor preserves the public unpack() contract, and the InferenceEvalCallback loop now correctly exits on the first terminal generation status. The new test in test_callbacks.py validates the break behaviour directly. No incorrect data, lost state, or broken contracts were found.

No files require special attention beyond the minor OverflowError gap in stats.py noted in the inline comment.

Important Files Changed

Filename Overview
src/nemo_safe_synthesizer/training/callbacks.py Refactored InferenceEvalCallback loop to use continue/break instead of was_stopped flag, correctly exiting on terminal generation status. Added explicit return None to on_step_end.
src/nemo_safe_synthesizer/data_processing/records/json_record.py Added init override to call _unpack_json() at construction; preserved public unpack() method that resets and re-unpacks. Added explicit return None to value_for_json_path and value_for_value_path.
src/nemo_safe_synthesizer/pii_replacer/ner/models.py Replaced chain-of-responsibility loop over self.obj_from_fs with a direct method call; updated None check from truthiness to explicit is None; fixed typo in error message.
src/nemo_safe_synthesizer/evaluation/statistics/stats.py Narrowed exception types in get_numeric_distribution_bins from bare Exception to (TypeError, ValueError); now explicitly initialises bins to empty array on exception.
src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py Changed sequential try/except (ast then json.loads always) to nested try/except (json.loads only on ast failure); foreach_itr is now explicitly set to None when both parsers fail.
src/nemo_safe_synthesizer/generation/vllm_backend.py Added defensive None check on result after inner match statement and improved debug logging for ImportError and teardown failures.
src/nemo_safe_synthesizer/data_processing/records/base.py Removed self.unpack() call from BaseRecord.init; subclasses are now responsible for calling unpack at construction.
src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py Added explicit return {} after ValidationError in _try_extract_entities; removed dead last_log = monotonic() update after the final post-loop log block.
tests/training/test_callbacks.py Added TestInferenceEvalCallbackTerminalStatus class verifying that a no-records batch stops generation after exactly one generate() call and sets control.should_training_stop.

Flowchart

%%{init: {'theme': 'neutral'}}%%
flowchart TD
    A[on_evaluate triggered] --> B[for _ in range num_batches]
    B --> C[generate batch]
    C --> D{generation.status}
    D -->|IN_PROGRESS| E[continue → next iteration]
    E --> B
    D -->|STOP_NO_RECORDS| F[control.should_training_stop = True]
    D -->|STOP_METRIC_REACHED| G[control.should_training_stop = True]
    D -->|other terminal| H[control.should_training_stop = True]
    F --> I[log error + append training_incomplete: no_records]
    G --> J[log error + append training_incomplete: stopping_condition_reached]
    H --> K[no log appended]
    I --> L[break]
    J --> L
    K --> L
    L --> M[return]
Loading

Reviews (4): Last reviewed commit: "chore: back out a handful per kendrick c..." | Re-trigger Greptile

Comment on lines +174 to +193
if self.generation.status == GenerationStatus.IN_PROGRESS:
continue

control.should_training_stop = True
if self.generation.status == GenerationStatus.STOP_NO_RECORDS:
logger.error(
"🛑 Stopping generation prematurely. No records were generated. "
"Please consider adjusting the sampling parameters.",
)
state.log_history.append({"training_incomplete": "no_records"}) # ty: ignore[invalid-argument-type] -- HF Trainer expects dict[str, float] but we use str values for stop signals
elif self.generation.status == GenerationStatus.STOP_METRIC_REACHED:
stop_frac = (
(self.generation.stop_condition.last_value or 0.0) if self.generation.stop_condition else 0.0
)
logger.error(
"🛑 Stopping generation prematurely. The stopping "
"condition was reached with a running average invalid "
f"fraction of {stop_frac:.2%}",
)
state.log_history.append({"training_incomplete": "stopping_condition_reached"}) # ty: ignore[invalid-argument-type] -- HF Trainer expects dict[str, float] but we use str values for stop signals

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Missing break after stop condition is detected

After setting control.should_training_stop = True and logging the stop reason, the refactored code falls through to the end of the loop body without a break. The for _ in range(self.num_batches): loop then continues executing every remaining batch — generating outputs, logging the same stop-reason error message, and calling add_batch — for all iterations that haven't fired yet. The original code issued was_stopped = True; break to exit the loop immediately (even though the subsequent if was_stopped: block was dead code). A break is needed at the end of the stop-handling block to restore that early-exit behaviour and avoid duplicate error messages.

Signed-off-by: mkornfield <mkornfield@nvidia.com>
Signed-off-by: mkornfield <mkornfield@nvidia.com>
@mckornfield
mckornfield force-pushed the codeql-findings-sweep/mck branch from d151a77 to f0173e9 Compare May 21, 2026 17:03
@mckornfield mckornfield changed the title Codeql findings sweep/mck chore: sweep codeql findings and fix May 21, 2026
@mckornfield mckornfield changed the title chore: sweep codeql findings and fix chore: sweep codeql findings and fix May 21, 2026
@coderabbitai coderabbitai Bot added test Test-only addition or change security Security-relevant fix or hardening chore Maintenance not tied to a user-visible change refactor Internal restructuring with no behavior change and removed bug Defects in shipped behavior labels May 21, 2026

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

♻️ Duplicate comments (1)
src/nemo_safe_synthesizer/training/callbacks.py (1)

177-194: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Break after any terminal generation status.

When GenerationStatus.STOP_NO_RECORDS is hit, Line 177 already requests trainer shutdown, but this loop still keeps generating remaining batches. That can do extra model work and append multiple "no_records" markers in the same evaluation. Add a break after recording the stop reason.

Proposed fix
             if self.generation.status == GenerationStatus.STOP_NO_RECORDS:
                 logger.error(
                     "🛑 Stopping generation prematurely. No records were generated. "
                     "Please consider adjusting the sampling parameters.",
                 )
                 state.log_history.append({"training_incomplete": "no_records"})  # ty: ignore[invalid-argument-type] -- HF Trainer expects dict[str, float] but we use str values for stop signals
             elif self.generation.status == GenerationStatus.STOP_METRIC_REACHED:
                 stop_frac = (
                     (self.generation.stop_condition.last_value or 0.0) if self.generation.stop_condition else 0.0
                 )
                 logger.error(
                     "🛑 Stopping generation prematurely. The stopping "
                     "condition was reached with a running average invalid "
                     f"fraction of {stop_frac:.2%}",
                 )
                 state.log_history.append({"training_incomplete": "stopping_condition_reached"})  # ty: ignore[invalid-argument-type] -- HF Trainer expects dict[str, float] but we use str values for stop signals
-                break
+            break

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: 2565361e-7aaa-4833-b48e-8e5f5e192d38

📥 Commits

Reviewing files that changed from the base of the PR and between d151a77 and f0173e9.

📒 Files selected for processing (40)
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/cli/run.py
  • src/nemo_safe_synthesizer/config/autoconfig.py
  • src/nemo_safe_synthesizer/config/replace_pii.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/configurator/parameters.py
  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/data_processing/records/base.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • tests/cli/test_run.py
  • tests/conftest.py
  • tests/e2e/test_dataset_config.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/generation/test_batch.py
  • tests/generation/test_vllm_backend.py
  • tests/observability/test_observability.py
  • tests/preflight/test_plugin_registration.py
  • tests/telemetry/test_telemetry.py
  • tools/codestyle/copyright_fixer.py
💤 Files with no reviewable changes (4)
  • src/nemo_safe_synthesizer/config/replace_pii.py
  • src/nemo_safe_synthesizer/data_processing/records/base.py
  • src/nemo_safe_synthesizer/configurator/parameters.py
  • tests/generation/test_vllm_backend.py
✅ Files skipped from review due to trivial changes (9)
  • src/nemo_safe_synthesizer/llm/metadata.py
  • src/nemo_safe_synthesizer/config/autoconfig.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/labels.py
  • src/nemo_safe_synthesizer/cli/run.py
  • tests/preflight/test_plugin_registration.py
  • tests/conftest.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/person_name.py
  • tools/codestyle/copyright_fixer.py
  • tests/observability/test_observability.py
📜 Review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (4)
  • GitHub Check: Unit Tests (3.13)
  • GitHub Check: Smoke Tests
  • GitHub Check: Unit Tests (3.12)
  • GitHub Check: Unit Tests (3.11)
🧰 Additional context used
📓 Path-based instructions (15)
**/*.{md,markdown,py}

📄 CodeRabbit inference engine (.cursor/rules/agent-markdown-style.mdc)

**/*.{md,markdown,py}: Avoid decorative bold (**text**) in list items, body text, and docstrings; use structural cues (headers, list markers, colons, backticks) for emphasis instead
Use backticks for code identifiers, paths, and CLI commands in markdown and docstrings

Files:

  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • tests/cli/test_run.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • tests/generation/test_batch.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
**/*.py

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

**/*.py: Use American English spelling: 'initialize' not 'initialise', 'recognize' not 'recognise', 'color' not 'colour'.
Use observability.get_logger(__name__) for logging, never logging.getLogger() or structlog.get_logger() directly.
Use category loggers: .runtime for internals, .user for progress/results, .system for system events.
Never use print() for operational output. Use click.echo() for CLI output or sys.stdout.write() for raw output in tools.
Use extra={} in logging for structured data that downstream tools should query or aggregate; use f-strings for human-readable context.
Raise from the custom error hierarchy with dual inheritance: SafeSynthesizerError (base), UserError, DataError, ParameterError, GenerationError, InternalError.
Use NSSBaseModel for config/parameter models in config/ which define user-facing configuration. Use raw BaseModel or module-specific bases for data transfer objects and internal structures.
Use BaseSettings for env/CLI settings. Prefer AliasChoices on individual fields when a field needs to respond to both its Python name and an env var name.
Include Field(description=...) for Pydantic model fields as the canonical field docstring for API documentation and CLI help text.
Use assignment-style type = Field(default=..., description="...") as the default for Pydantic model fields because type checkers understand default, default_factory, and alias in assignment style.
Use Annotated only when the field carries additional metadata beyond Field() -- ValueValidator, AutoParam, DependsOnValidator, reusable constrained type aliases, nested-type constraints, or discriminated unions.
Put defaults as bare assignment (= value), not inside Field(default=...), when using Annotated. Exception: use assignment-style Field(default_factory=...) for defaults that cannot be expressed as bare assignments.
Use @dataclass(frozen=True) for immutable value objects and validators; mu...

Files:

  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • tests/cli/test_run.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • tests/generation/test_batch.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
src/**/*.py

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

src/**/*.py: Use relative imports in src/ (e.g., from ..observability import get_logger).
Do not use print() statements in library code. Use get_logger(__name__) from observability.py or click.echo() for CLI.
Do not use assert for validation in library code. Use if/raise for input validation. assert statements can be stripped by -O and must never guard correctness.

Files:

  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py

⚙️ CodeRabbit configuration file

Review library code against STYLE_GUIDE.md. Focus on behavior, API contracts, error handling, resource cleanup, typing, logging, and user-facing failures. Public APIs and nontrivial functions need Google-style docstrings.

Files:

  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
**/*.{py,sh,yaml,yml}

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

Include SPDX copyright header at the top: # SPDX-FileCopyrightText: Copyright (c) 2025-2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved. and # SPDX-License-Identifier: Apache-2.0. The make format command handles this automatically.

Files:

  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • tests/cli/test_run.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • tests/generation/test_batch.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
**/*

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

**/*: Include a newline at the end of all files, never trailing whitespace. This is enforced by pre-commit.
Use line length of 120 characters for code, comments, and docstrings (configured in ruff.toml).

Files:

  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • tests/cli/test_run.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • tests/generation/test_batch.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py

⚙️ CodeRabbit configuration file

**/*: Review as a senior maintainer for NeMo Safe Synthesizer. Prioritize issues that can change behavior, break user workflows, weaken privacy guarantees, hide failures, make tests unreliable, or create maintenance risk. Avoid generic style commentary unless it points to a concrete project convention that automated tools will not catch.
Comment only when the finding is actionable and tied to changed code. For each finding, state the impact, the condition that triggers it, and the smallest practical fix. Prefer one precise comment over broad advice. Do not ask for refactors outside the PR scope unless the changed code creates the problem.
Review type guidance: - Potential issue: use for correctness bugs, data loss, privacy leaks,
security risks, broken public APIs, invalid config behavior, missing
validation, hidden failures, nondeterministic tests, or CI breakage.

  • Refactor suggestion: use for local maintainability problems introduced
    by the diff when they have clear future cost, such as duplicated setup,
    unclear boundaries, over-mocking, avoidable complexity, or opaque test
    helpers.
  • Nitpick: avoid in chill mode. Do not emit formatting, import-order,
    wording, or style-only comments unless automated tools cannot catch the
    issue and it affects maintainability.

Severity guidance: - Critical: security/privacy leaks, data loss, training/test/holdout
contamination, or broken release/package/core pipeline execution.

  • Major: incorrect generation/training/evaluation behavior, broken
    CLI/SDK public API, invalid config defaults or validators, or GPU/vLLM
    cleanup and process-isolation bugs likely to fail CI or production
    runs.
  • Minor: localized bugs, missing focused tests for changed behavior, or
    bad test patterns that weaken regression coverage.
  • Trivial: small cleanup with no behavior impact. Usually suppress in
    chill mode.
  • Info: context only. Avoid unless it helps reviewers understand risk.
    Safe-Synthesizer-specific review focus: - Data ...

Files:

  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
  • tests/e2e/test_dataset_config.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • tests/cli/test_run.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/sdk/config_builder.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • tests/generation/test_batch.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/cli/artifact_structure.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/configurator/parameter.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/observability.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
src/nemo_safe_synthesizer/data_processing/**/*.py

⚙️ CodeRabbit configuration file

Review for data-contract regressions. Check input/training/test/synthetic naming, group boundaries, token-budget math, record ordering, schema and column validation, nullable dtypes, and deterministic behavior.

Files:

  • src/nemo_safe_synthesizer/data_processing/actions/data_actions.py
  • src/nemo_safe_synthesizer/data_processing/actions/dates.py
  • src/nemo_safe_synthesizer/data_processing/records/json_record.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
src/nemo_safe_synthesizer/privacy/**/*.py

⚙️ CodeRabbit configuration file

Treat privacy changes as high-risk. Check DP accounting, parameter validation, data leakage, seed handling, model state persistence, and whether privacy guarantees are documented accurately.

Files:

  • src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py
  • src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py
tests/**

📄 CodeRabbit inference engine (.cursor/rules/repo-navigation.mdc)

Tests should mirror the src/ directory structure in tests/

Files:

  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • tests/e2e/test_dataset_config.py
  • tests/cli/test_run.py
  • tests/generation/test_batch.py
tests/**/*.py

📄 CodeRabbit inference engine (.cursor/rules/repo-navigation.mdc)

Tests in tests/e2e/ should be auto-marked with e2e marker, tests in tests/smoke/ with smoke marker, others with unit marker

tests/**/*.py: Use absolute imports in tests/ (e.g., from nemo_safe_synthesizer.observability import get_logger).
Use fixture_ prefix convention for fixtures for grep-ability and to separate fixtures from test functions. Add a one-line docstring describing the fixture's purpose and data.
Use function-scoped fixtures by default. Session scope only when empirically justified by test runtime.
Use bare assert as the primary assertion style; pytest.raises() with match= for exceptions; pytest.approx() for floating-point comparisons.
Mark CUDA-dependent tests with @pytest.mark.e2e, @pytest.mark.smoke, or @pytest.mark.requires_gpu.
Mock only external boundaries, not internal implementation details.
Ensure test isolation: no shared mutable state or execution-order dependencies between tests. If something must be run first before executing a test, include it in the test or a fixture.
Use @pytest.mark.parametrize for testing multiple input combinations rather than copy-pasting similar tests.

Organize tests using pytest following the structure in tests/TESTING.md with support for unit tests, smoke tests, and end-to-end tests

Files:

  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • tests/e2e/test_dataset_config.py
  • tests/cli/test_run.py
  • tests/generation/test_batch.py

⚙️ CodeRabbit configuration file

Review tests against tests/TESTING.md. Check marker usage, fixture naming, tmp_path usage, determinism, and GPU/vLLM process-isolation requirements. Flag slop tests that only check that code runs, assert result is not None when stronger invariants exist, over-mock internal implementation details, patch around the bug instead of reproducing it, or add broad snapshot/golden churn without a clear contract. Flag change detector tests that fail on harmless refactors, formatting, record ordering, incidental wording, or private implementation details without demonstrating a behavior regression. Prefer existing fixtures or focused new fixtures for repeated setup; keep tests DRY when reasonable without making the behavior under test opaque. print() is allowed in tests.

Files:

  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • tests/e2e/test_dataset_config.py
  • tests/cli/test_run.py
  • tests/generation/test_batch.py
**/*test*.py

📄 CodeRabbit inference engine (AGENTS.md)

The unit_test marker is deprecated; use unit instead

Files:

  • tests/e2e/test_safe_synthesizer.py
  • tests/telemetry/test_telemetry.py
  • tests/e2e/test_dataset_config.py
  • tests/cli/test_run.py
  • tests/generation/test_batch.py
src/nemo_safe_synthesizer/evaluation/**/*.py

⚙️ CodeRabbit configuration file

Treat evaluation changes as correctness-sensitive. Check metric inputs, holdout usage, privacy metric semantics, report data shape, missing-data handling, and whether unavailable metrics fail or degrade intentionally.

Files:

  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py
  • src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py
src/nemo_safe_synthesizer/pii_replacer/**/*.py

⚙️ CodeRabbit configuration file

Treat PII replacement changes as high-risk. Check entity coverage, replacement determinism, leakage of original values, handling of empty or multilingual text, and compatibility with optional dependencies.

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/model.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
src/nemo_safe_synthesizer/generation/**/*.py

⚙️ CodeRabbit configuration file

Review generation changes for retry loops, stopping conditions, invalid record handling, regex/structured output contracts, backend teardown, memory cleanup, and vLLM assumptions.

Files:

  • src/nemo_safe_synthesizer/generation/regex_manager.py
  • src/nemo_safe_synthesizer/generation/vllm_backend.py
src/nemo_safe_synthesizer/configurator/**/*.py

⚙️ CodeRabbit configuration file

Review Pydantic-to-Click mapping carefully. Check option names, type conversion, nullable sub-config behavior, validation errors, help text, and compatibility with parse_overrides().

Files:

  • src/nemo_safe_synthesizer/configurator/parameter.py
src/nemo_safe_synthesizer/training/**/*.py

⚙️ CodeRabbit configuration file

Review training changes for dataset preprocessing, model path handling, artifact writes, LoRA/DP behavior, GPU memory usage, reproducibility, and cleanup on failure.

Files:

  • src/nemo_safe_synthesizer/training/callbacks.py
🪛 Ruff (0.15.13)
src/nemo_safe_synthesizer/evaluation/statistics/stats.py

[warning] 153-153: Do not catch blind exception: Exception

(BLE001)

src/nemo_safe_synthesizer/data_processing/dataset.py

[warning] 78-78: Do not catch blind exception: Exception

(BLE001)

🔇 Additional comments (22)
src/nemo_safe_synthesizer/data_processing/actions/data_actions.py (1)

528-528: LGTM!

src/nemo_safe_synthesizer/privacy/dp_transformers/privacy_args.py (1)

314-314: LGTM!

tests/e2e/test_safe_synthesizer.py (1)

13-13: LGTM!

Also applies to: 30-30

tests/telemetry/test_telemetry.py (1)

5-5: LGTM!

Also applies to: 28-29

src/nemo_safe_synthesizer/privacy/dp_transformers/dp_utils.py (1)

171-171: LGTM!

tests/e2e/test_dataset_config.py (1)

5-5: LGTM!

Also applies to: 22-22

src/nemo_safe_synthesizer/data_processing/actions/dates.py (1)

373-373: LGTM!

Also applies to: 396-396, 436-436

tests/cli/test_run.py (1)

6-6: LGTM!

Also applies to: 21-22

src/nemo_safe_synthesizer/sdk/config_builder.py (1)

129-129: LGTM!

src/nemo_safe_synthesizer/pii_replacer/ner/datetime.py (1)

128-129: LGTM!

tests/generation/test_batch.py (1)

4-4: LGTM!

Also applies to: 17-17, 204-204

src/nemo_safe_synthesizer/data_processing/records/json_record.py (1)

109-125: LGTM!

Also applies to: 131-131, 138-138

src/nemo_safe_synthesizer/cli/artifact_structure.py (1)

26-26: LGTM!

Also applies to: 82-82, 174-174, 232-232, 235-235, 293-293

src/nemo_safe_synthesizer/pii_replacer/data_editor/detect.py (1)

317-317: LGTM!

src/nemo_safe_synthesizer/generation/regex_manager.py (1)

290-290: LGTM!

Also applies to: 323-323

src/nemo_safe_synthesizer/evaluation/components/attribute_inference_protection.py (1)

195-195: LGTM!

src/nemo_safe_synthesizer/configurator/parameter.py (1)

98-98: LGTM!

src/nemo_safe_synthesizer/evaluation/components/text_semantic_similarity.py (1)

253-253: LGTM!

Also applies to: 442-446

src/nemo_safe_synthesizer/pii_replacer/ner/custom.py (1)

84-85: LGTM!

src/nemo_safe_synthesizer/generation/vllm_backend.py (1)

102-102: LGTM!

Also applies to: 188-188, 314-314, 451-453, 456-456

src/nemo_safe_synthesizer/pii_replacer/data_editor/edit.py (1)

271-274: LGTM!

src/nemo_safe_synthesizer/pii_replacer/ner/model.py (1)

74-74: LGTM!

Comment thread src/nemo_safe_synthesizer/data_processing/dataset.py Outdated
Comment thread src/nemo_safe_synthesizer/evaluation/statistics/stats.py
Comment thread src/nemo_safe_synthesizer/pii_replacer/ner/custom.py Outdated
Comment thread src/nemo_safe_synthesizer/pii_replacer/ner/models.py Outdated
Signed-off-by: mkornfield <mkornfield@nvidia.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
tests/training/test_callbacks.py (1)

169-193: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Add the required test category marker.

The new test has no category marker. Add exactly one (likely @pytest.mark.unit) to satisfy test marker policy and keep CI selection deterministic.

Proposed fix
 class TestInferenceEvalCallbackTerminalStatus:
     """Ensure terminal generation states stop the evaluation loop immediately."""
 
+    `@pytest.mark.unit`
     def test_callback_stops_after_no_records_status(
         self,
         fixture_mock_metadata,
         fixture_mock_processor,
         fixture_mock_model,

As per coding guidelines, "Marker rules: each test should have exactly one category marker among unit, smoke, e2e."


ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: 5b0cffc9-4431-4cd8-93e1-8d3c9a941ae2

📥 Commits

Reviewing files that changed from the base of the PR and between f0173e9 and b99c1c7.

📒 Files selected for processing (6)
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • tests/training/test_callbacks.py
📜 Review details
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (4)
  • GitHub Check: Unit Tests (3.11)
  • GitHub Check: Smoke Tests
  • GitHub Check: Unit Tests (3.12)
  • GitHub Check: Unit Tests (3.13)
🧰 Additional context used
📓 Path-based instructions (12)
**/*.{md,markdown,py}

📄 CodeRabbit inference engine (.cursor/rules/agent-markdown-style.mdc)

**/*.{md,markdown,py}: Avoid decorative bold (**text**) in list items, body text, and docstrings; use structural cues (headers, list markers, colons, backticks) for emphasis instead
Use backticks for code identifiers, paths, and CLI commands in markdown and docstrings

Files:

  • tests/training/test_callbacks.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
tests/**

📄 CodeRabbit inference engine (.cursor/rules/repo-navigation.mdc)

Tests should mirror the src/ directory structure in tests/

Files:

  • tests/training/test_callbacks.py
tests/**/*.py

📄 CodeRabbit inference engine (.cursor/rules/repo-navigation.mdc)

Tests in tests/e2e/ should be auto-marked with e2e marker, tests in tests/smoke/ with smoke marker, others with unit marker

tests/**/*.py: Use absolute imports in tests/ (e.g., from nemo_safe_synthesizer.observability import get_logger).
Use fixture_ prefix convention for fixtures for grep-ability and to separate fixtures from test functions. Add a one-line docstring describing the fixture's purpose and data.
Use function-scoped fixtures by default. Session scope only when empirically justified by test runtime.
Use bare assert as the primary assertion style; pytest.raises() with match= for exceptions; pytest.approx() for floating-point comparisons.
Mark CUDA-dependent tests with @pytest.mark.e2e, @pytest.mark.smoke, or @pytest.mark.requires_gpu.
Mock only external boundaries, not internal implementation details.
Ensure test isolation: no shared mutable state or execution-order dependencies between tests. If something must be run first before executing a test, include it in the test or a fixture.
Use @pytest.mark.parametrize for testing multiple input combinations rather than copy-pasting similar tests.

Organize tests using pytest following the structure in tests/TESTING.md with support for unit tests, smoke tests, and end-to-end tests

Files:

  • tests/training/test_callbacks.py

⚙️ CodeRabbit configuration file

Review tests against tests/TESTING.md. Check marker usage, fixture naming, tmp_path usage, determinism, and GPU/vLLM process-isolation requirements. Flag slop tests that only check that code runs, assert result is not None when stronger invariants exist, over-mock internal implementation details, patch around the bug instead of reproducing it, or add broad snapshot/golden churn without a clear contract. Flag change detector tests that fail on harmless refactors, formatting, record ordering, incidental wording, or private implementation details without demonstrating a behavior regression. Prefer existing fixtures or focused new fixtures for repeated setup; keep tests DRY when reasonable without making the behavior under test opaque. print() is allowed in tests.

Files:

  • tests/training/test_callbacks.py
**/*.py

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

**/*.py: Use American English spelling: 'initialize' not 'initialise', 'recognize' not 'recognise', 'color' not 'colour'.
Use observability.get_logger(__name__) for logging, never logging.getLogger() or structlog.get_logger() directly.
Use category loggers: .runtime for internals, .user for progress/results, .system for system events.
Never use print() for operational output. Use click.echo() for CLI output or sys.stdout.write() for raw output in tools.
Use extra={} in logging for structured data that downstream tools should query or aggregate; use f-strings for human-readable context.
Raise from the custom error hierarchy with dual inheritance: SafeSynthesizerError (base), UserError, DataError, ParameterError, GenerationError, InternalError.
Use NSSBaseModel for config/parameter models in config/ which define user-facing configuration. Use raw BaseModel or module-specific bases for data transfer objects and internal structures.
Use BaseSettings for env/CLI settings. Prefer AliasChoices on individual fields when a field needs to respond to both its Python name and an env var name.
Include Field(description=...) for Pydantic model fields as the canonical field docstring for API documentation and CLI help text.
Use assignment-style type = Field(default=..., description="...") as the default for Pydantic model fields because type checkers understand default, default_factory, and alias in assignment style.
Use Annotated only when the field carries additional metadata beyond Field() -- ValueValidator, AutoParam, DependsOnValidator, reusable constrained type aliases, nested-type constraints, or discriminated unions.
Put defaults as bare assignment (= value), not inside Field(default=...), when using Annotated. Exception: use assignment-style Field(default_factory=...) for defaults that cannot be expressed as bare assignments.
Use @dataclass(frozen=True) for immutable value objects and validators; mu...

Files:

  • tests/training/test_callbacks.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
**/*.{py,sh,yaml,yml}

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

Include SPDX copyright header at the top: # SPDX-FileCopyrightText: Copyright (c) 2025-2026 NVIDIA CORPORATION & AFFILIATES. All rights reserved. and # SPDX-License-Identifier: Apache-2.0. The make format command handles this automatically.

Files:

  • tests/training/test_callbacks.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
**/*

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

**/*: Include a newline at the end of all files, never trailing whitespace. This is enforced by pre-commit.
Use line length of 120 characters for code, comments, and docstrings (configured in ruff.toml).

Files:

  • tests/training/test_callbacks.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py

⚙️ CodeRabbit configuration file

**/*: Review as a senior maintainer for NeMo Safe Synthesizer. Prioritize issues that can change behavior, break user workflows, weaken privacy guarantees, hide failures, make tests unreliable, or create maintenance risk. Avoid generic style commentary unless it points to a concrete project convention that automated tools will not catch.
Comment only when the finding is actionable and tied to changed code. For each finding, state the impact, the condition that triggers it, and the smallest practical fix. Prefer one precise comment over broad advice. Do not ask for refactors outside the PR scope unless the changed code creates the problem.
Review type guidance: - Potential issue: use for correctness bugs, data loss, privacy leaks,
security risks, broken public APIs, invalid config behavior, missing
validation, hidden failures, nondeterministic tests, or CI breakage.

  • Refactor suggestion: use for local maintainability problems introduced
    by the diff when they have clear future cost, such as duplicated setup,
    unclear boundaries, over-mocking, avoidable complexity, or opaque test
    helpers.
  • Nitpick: avoid in chill mode. Do not emit formatting, import-order,
    wording, or style-only comments unless automated tools cannot catch the
    issue and it affects maintainability.

Severity guidance: - Critical: security/privacy leaks, data loss, training/test/holdout
contamination, or broken release/package/core pipeline execution.

  • Major: incorrect generation/training/evaluation behavior, broken
    CLI/SDK public API, invalid config defaults or validators, or GPU/vLLM
    cleanup and process-isolation bugs likely to fail CI or production
    runs.
  • Minor: localized bugs, missing focused tests for changed behavior, or
    bad test patterns that weaken regression coverage.
  • Trivial: small cleanup with no behavior impact. Usually suppress in
    chill mode.
  • Info: context only. Avoid unless it helps reviewers understand risk.
    Safe-Synthesizer-specific review focus: - Data ...

Files:

  • tests/training/test_callbacks.py
  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
**/*test*.py

📄 CodeRabbit inference engine (AGENTS.md)

The unit_test marker is deprecated; use unit instead

Files:

  • tests/training/test_callbacks.py
src/**/*.py

📄 CodeRabbit inference engine (STYLE_GUIDE.md)

src/**/*.py: Use relative imports in src/ (e.g., from ..observability import get_logger).
Do not use print() statements in library code. Use get_logger(__name__) from observability.py or click.echo() for CLI.
Do not use assert for validation in library code. Use if/raise for input validation. assert statements can be stripped by -O and must never guard correctness.

Files:

  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py

⚙️ CodeRabbit configuration file

Review library code against STYLE_GUIDE.md. Focus on behavior, API contracts, error handling, resource cleanup, typing, logging, and user-facing failures. Public APIs and nontrivial functions need Google-style docstrings.

Files:

  • src/nemo_safe_synthesizer/data_processing/dataset.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
  • src/nemo_safe_synthesizer/training/callbacks.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
src/nemo_safe_synthesizer/data_processing/**/*.py

⚙️ CodeRabbit configuration file

Review for data-contract regressions. Check input/training/test/synthetic naming, group boundaries, token-budget math, record ordering, schema and column validation, nullable dtypes, and deterministic behavior.

Files:

  • src/nemo_safe_synthesizer/data_processing/dataset.py
src/nemo_safe_synthesizer/pii_replacer/**/*.py

⚙️ CodeRabbit configuration file

Treat PII replacement changes as high-risk. Check entity coverage, replacement determinism, leakage of original values, handling of empty or multilingual text, and compatibility with optional dependencies.

Files:

  • src/nemo_safe_synthesizer/pii_replacer/ner/custom.py
  • src/nemo_safe_synthesizer/pii_replacer/ner/models.py
src/nemo_safe_synthesizer/evaluation/**/*.py

⚙️ CodeRabbit configuration file

Treat evaluation changes as correctness-sensitive. Check metric inputs, holdout usage, privacy metric semantics, report data shape, missing-data handling, and whether unavailable metrics fail or degrade intentionally.

Files:

  • src/nemo_safe_synthesizer/evaluation/statistics/stats.py
src/nemo_safe_synthesizer/training/**/*.py

⚙️ CodeRabbit configuration file

Review training changes for dataset preprocessing, model path handling, artifact writes, LoRA/DP behavior, GPU memory usage, reproducibility, and cleanup on failure.

Files:

  • src/nemo_safe_synthesizer/training/callbacks.py
🔇 Additional comments (6)
tests/training/test_callbacks.py (1)

63-80: LGTM!

src/nemo_safe_synthesizer/data_processing/dataset.py (1)

67-80: LGTM!

src/nemo_safe_synthesizer/pii_replacer/ner/custom.py (1)

143-149: LGTM!

Also applies to: 181-187

src/nemo_safe_synthesizer/evaluation/statistics/stats.py (1)

62-64: LGTM!

Also applies to: 147-154

src/nemo_safe_synthesizer/training/callbacks.py (1)

174-194: LGTM!

src/nemo_safe_synthesizer/pii_replacer/ner/models.py (1)

199-200: LGTM!

@kendrickb-nvidia kendrickb-nvidia left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Need to look at the epsilon calculation change as I suspect that introduces a bug.

Overall, what's the reasoning for some of these, and I think we should add the common patterns to the STYLE_GUIDE.md.

  • importlib usage in tests
  • Never using pass on an except (I guess that's the assumption here, but it makes for some odd code)
  • Adding raise AssertionError("unreachable") after match statements, even when a wildcard case is present.

return _type_regex(instance, whitespace_pattern, **kwargs)
case _:
raise NotImplementedError()
raise AssertionError("unreachable")

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: This feels pretty weird to add this raise immediately after a wildcard case.

I guess thinking the cases may change in the future so this raise will always be here. But meh, that's the whole point of the wildcard case. Cleaner to remove the wildcard case and just raise NotImplementedError() as the last line instead maybe?

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yeah... these unreachable statement ones feel like a reach to me, there might be a better way to handle them (or they might just be false positives)

return result
case _:
raise ValueError("input ids are not a tensor or list!")
raise AssertionError("unreachable")

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: Another where should just put the ValueError raise at the top level and remove the wildcard match if we don't trust/believe the wildcard match.

eps_R = compute_epsilon(mu_R)[2]
except (OverflowError, RuntimeError):
pass
eps_R = float("inf")

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

suggestion: I don't think this change is correct and should stay as pass (or switch to break). If we've already calculated an eps_R and mu_R, I suspect we want to leave it unchanged (and definitely seems bad to change one but not the other). @andreatgretel can you help confirm.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can put it back. I'll just dismiss the empty except warnings, esp if this breaks things

return cls(**overrides)
case _:
raise TypeError(f"Unsupported config type: {type(values)}")
raise AssertionError("unreachable")

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: Again, let's just not use the match case wildcard then.

return "plain"
except (ImportError, AttributeError):
pass
return "json"

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: Why do we need to change this?

If we put the return here, then remove the return on 151, right?

Comment thread tests/cli/test_run.py Outdated
from nemo_safe_synthesizer.telemetry import DeploymentTypeEnum, TaskStatusEnum
from nemo_safe_synthesizer.tooling import PreflightRenderContext

importlib.import_module("nemo_safe_synthesizer.sdk.library_builder") # ensure submodule is loaded for mock.patch

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

question: What's more reliable about using importlib vs existing? Using importlib just to remove a # noqa: F401 seems unnecessary to me.

Signed-off-by: mkornfield <mkornfield@nvidia.com>
@mckornfield
mckornfield merged commit cf1900c into main May 26, 2026
19 of 20 checks passed
@mckornfield
mckornfield deleted the codeql-findings-sweep/mck branch May 26, 2026 20:17
@coderabbitai coderabbitai Bot mentioned this pull request May 26, 2026
7 tasks
@coderabbitai coderabbitai Bot mentioned this pull request Jun 24, 2026
1 task
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

chore Maintenance not tied to a user-visible change refactor Internal restructuring with no behavior change security Security-relevant fix or hardening test Test-only addition or change

Projects

None yet

Development

Successfully merging this pull request may close these issues.

chore: add CodeQL or SAST security scanning

2 participants