Repository navigation
refactor(nodes): replace print statements with structured logging [OMN-701] - #187
Conversation
WalkthroughAdds a pre-commit hook and a new AST-based CLI to detect Changes
Sequence Diagram(s)sequenceDiagram
participant Dev as Developer (git)
participant Hook as pre-commit hook
participant CLI as check_no_print_statements.py
participant FS as Repo files (staged `src/*.py`)
participant Console as Console / Exit
Dev->>Hook: git commit (pre-commit runs)
Hook->>CLI: execute `poetry run python scripts/validation/check_no_print_statements.py` (pass filenames)
CLI->>FS: read staged Python files (source + lines)
CLI->>CLI: parse AST, inspect Call nodes, analyze docstrings, apply `# print-ok:` exemptions
CLI->>Console: print errors/warnings summary
alt errors found
Console->>Hook: exit non-zero (block commit)
else only warnings or none
Console->>Hook: exit zero (allow commit)
end
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~30 minutes
Poem
Pre-merge checks and finishing touches✅ Passed checks (3 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
Comment |
Code Review - PR #187: Replace print statements with structured loggingOverviewThis PR successfully addresses OMN-701 by removing all 16 print() statements from production node implementations and replacing them with appropriate structured logging calls. The addition of a pre-commit validation hook is a strong preventative measure. ✅ Strengths
🔍 Issues & Recommendations1. CRITICAL: Missing Logger Import in Docstrings (node_effect.py:126-167)The updated docstring example in import logging
logger = logging.getLogger(__name__)Issue: This creates a module-level logger in the example, but the actual Recommendation: Update the docstring example to either:
Location: src/omnibase_core/nodes/node_effect.py:126-167 2. Minor: Validation Script Could Be More RobustIssue: Recommendation: Consider adding a test case for this edge case in the validation script's test suite (if one exists or will be created). Severity: Low (unlikely to occur in practice) 3. Documentation: Pre-commit Hook TestingQuestion: The PR description mentions "Pre-commit hooks pass (37 hooks)" but doesn't show evidence of the new hook being tested with actual violations. Recommendation: Consider adding to the PR description or comments:
Severity: Low (nice-to-have for documentation) 4. Code Quality: Magic Numbers in Validation ScriptIssue: Lines 218, 220 use magic number Recommendation: Extract to a constant: _OUTPUT_WIDTH = 60
print(f"\n{'=' * _OUTPUT_WIDTH}")Location: scripts/validation/check_no_print_statements.py:218-220 Severity: Very Low (style/maintainability) 🧪 Testing Recommendations
📊 Impact AssessmentPositive:
Risks:
Performance: No impact (logging calls are already optimized in omnibase_core) Security: No impact Backwards Compatibility: No impact (internal refactoring only) 🎯 Recommendation: APPROVE with minor fixThis is a solid code quality improvement with excellent preventative tooling. The only blocker is the misleading logger example in Action Items:
📚 References
Overall: Great work! This PR demonstrates excellent attention to detail and proactive engineering (the validation hook is particularly well done). 🎉 |
There was a problem hiding this comment.
Actionable comments posted: 1
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (5)
.pre-commit-config.yaml(1 hunks)scripts/validation/check_no_print_statements.py(1 hunks)src/omnibase_core/nodes/node_effect.py(2 hunks)src/omnibase_core/nodes/node_orchestrator.py(4 hunks)src/omnibase_core/nodes/node_reducer.py(5 hunks)
🧰 Additional context used
📓 Path-based instructions (3)
**/*.py
📄 CodeRabbit inference engine (CLAUDE.md)
**/*.py: Always use Poetry for Python package management and task execution - usepoetry runfor all Python commands (pytest, mypy, black, isort, etc.), never use pip or direct python execution
Callsuper().__init__(container)in all node class constructors - this is MANDATORY and eliminates 80+ lines of boilerplate initialization code
Always raise structured errors using ModelOnexError with appropriate EnumCoreErrorCode, never use generic Exception
Usecontainer.get_service("ProtocolName")for dependency injection - always use protocol names, never concrete class names or isinstance checks
Use @standard_error_handling decorator on methods to eliminate 6+ lines of try/catch boilerplate
Do NOT share node instances across threads - use thread-local instances or separate instances per thread for NodeCompute, NodeEffect, NodeReducer, NodeOrchestrator
Use FileRegistry for loading RuntimeHostContract YAML files - handles fail-fast error reporting with specific error codes (FILE_NOT_FOUND, CONFIGURATION_PARSE_ERROR, CONTRACT_VALIDATION_ERROR, etc.)
Use the correct container type: ModelONEXContainer for dependency injection in node constructors, ModelContainer[T] only for wrapping single values with metadata
Use EnumNodeKind for architectural classification (EFFECT, COMPUTE, REDUCER, ORCHESTRATOR) and EnumNodeType for specific implementation type (TRANSFORMER, AGGREGATOR, GATEWAY, etc.)
Format code usingpoetry run blackand sort imports usingpoetry run isortbefore committing
Lint code usingpoetry run ruff checkto detect issues and apply auto-fixes withpoetry run ruff check --fix
Files:
src/omnibase_core/nodes/node_reducer.pysrc/omnibase_core/nodes/node_orchestrator.pysrc/omnibase_core/nodes/node_effect.pyscripts/validation/check_no_print_statements.py
src/omnibase_core/**/*.py
📄 CodeRabbit inference engine (CLAUDE.md)
src/omnibase_core/**/*.py: Achieve and maintain 100% mypy strict mode compliance with 0 errors across all source files
Achieve and maintain pyright basic mode compliance with 0 errors (targets Python 3.12)
For immutable value objects that are nested in other Pydantic models or used in parallel test execution, addfrom_attributes=Trueto ConfigDict
Use protocol-based dependency injection with container.get_service() - no isinstance checks with protocols (rely on duck typing instead)
Files:
src/omnibase_core/nodes/node_reducer.pysrc/omnibase_core/nodes/node_orchestrator.pysrc/omnibase_core/nodes/node_effect.py
src/omnibase_core/nodes/**/*.py
📄 CodeRabbit inference engine (CLAUDE.md)
Import nodes from
omnibase_core.nodesusing the unified import path - useNodeCompute,NodeReducer,NodeOrchestrator,NodeEffect(NOT with 'Declarative' suffix)
Files:
src/omnibase_core/nodes/node_reducer.pysrc/omnibase_core/nodes/node_orchestrator.pysrc/omnibase_core/nodes/node_effect.py
🧠 Learnings (6)
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: ModelIntent pattern should be used in REDUCER nodes for pure FSM transitions without direct side effects
Applied to files:
src/omnibase_core/nodes/node_reducer.py
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to src/omnibase_core/nodes/**/*.py : Import nodes from `omnibase_core.nodes` using the unified import path - use `NodeCompute`, `NodeReducer`, `NodeOrchestrator`, `NodeEffect` (NOT with 'Declarative' suffix)
Applied to files:
src/omnibase_core/nodes/node_reducer.pysrc/omnibase_core/nodes/node_orchestrator.pysrc/omnibase_core/nodes/node_effect.py
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to **/*.py : Format code using `poetry run black` and sort imports using `poetry run isort` before committing
Applied to files:
.pre-commit-config.yaml
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to **/*.py : Lint code using `poetry run ruff check` to detect issues and apply auto-fixes with `poetry run ruff check --fix`
Applied to files:
.pre-commit-config.yaml
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to **/*.py : Always use Poetry for Python package management and task execution - use `poetry run` for all Python commands (pytest, mypy, black, isort, etc.), never use pip or direct python execution
Applied to files:
.pre-commit-config.yaml
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to src/omnibase_core/**/*.py : Achieve and maintain pyright basic mode compliance with 0 errors (targets Python 3.12)
Applied to files:
.pre-commit-config.yaml
⏰ 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). (2)
- GitHub Check: Smoke Tests
- GitHub Check: claude-review
🔇 Additional comments (16)
src/omnibase_core/nodes/node_effect.py (2)
129-135: LGTM! Docstring example demonstrates structured logging best practices.The example correctly shows how to set up logging with
logging.getLogger(__name__)and uses the%splaceholder format which is idiomatic for Python logging (enables lazy evaluation).
166-169: Appropriate log levels for success/failure outcomes.Using
logger.info()for success confirmations andlogger.error()for failures aligns with the PR's log level guidelines.src/omnibase_core/nodes/node_reducer.py (5)
191-193: LGTM! Debug level appropriate for state transition details.Using
logger.debug()for FSM state and intent count information is correct as these are status details useful for debugging but not critical operational info.
256-260: Appropriate log levels for validation outcomes.
logger.warning()for validation failures andlogger.info()for success aligns with the PR's log level guidelines.
277-279: LGTM!
logger.info()is appropriate for FSM completion events.
292-294: LGTM!
logger.debug()is appropriate for state progression tracing.
307-309: LGTM!
logger.info()is appropriate for workflow completion notifications.src/omnibase_core/nodes/node_orchestrator.py (4)
149-151: LGTM! Debug level appropriate for execution metrics.Using
logger.debug()for step counts and action counts is correct for detailed execution tracing.
244-246: LGTM!Consistent use of
logger.debug()for status and action counts in docstring examples.
283-287: Consistent validation logging pattern.Same pattern as
node_reducer.pyusinglogger.warning()for failures andlogger.info()for success.
341-343: LGTM!
logger.debug()is appropriate for execution order details.scripts/validation/check_no_print_statements.py (4)
1-34: Well-documented module with clear rationale.The docstring clearly explains the purpose, detected patterns, usage, and rationale for the validation script.
37-91: LGTM! Clean AST visitor implementation.The
PrintStatementDetectorclass correctly:
- Detects direct
print()calls by checkingast.Namewithid == "print"- Supports exemptions via
# print-ok:comments on same line or line above- Uses
generic_visit()to continue traversal
156-193: LGTM! Robust file processing with proper error handling.The
check_filefunction correctly:
- Handles file read errors (OSError, UnicodeDecodeError)
- Handles syntax errors gracefully
- Combines AST-based detection with docstring checks
196-251: CLI output correctly uses# print-ok:exemptions.The
main()function appropriately uses# print-ok: CLI outputcomments for its own print statements since this is a CLI tool that needs to output to stdout. The exit code logic (fail on errors only, warnings don't block) is sensible..pre-commit-config.yaml (1)
301-311: LGTM! Hook configuration follows established patterns.The new
check-no-print-statementshook is correctly configured:
- Uses
poetry run pythonper coding guidelinespass_filenames: truefor efficient incremental checking- Appropriate exclusions for tests, archived, and validation scripts
- Pre-commit stage is appropriate for quick validation
…N-701] Replace all print() statements in node implementations with structured logging using Python's logging module for proper observability. Changes: - node_reducer.py: Replace 7 print() with logger.debug/info/warning - node_orchestrator.py: Replace 7 print() with logger.debug/info/warning - node_effect.py: Replace 2 print() with logger.info/error Prevention: - Add check_no_print_statements.py validation script - Add pre-commit hook to prevent future print() statements - Support # print-ok: comments for CLI tools that need print() The validation script uses AST parsing to accurately detect print() calls while ignoring comments and string literals. Reference: OMNIBASE_CORE_CODE_QUALITY_AUDIT.md - Section 2
5118cd5 to
08ea79b
Compare
There was a problem hiding this comment.
Actionable comments posted: 2
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (7)
.pre-commit-config.yaml(1 hunks)scripts/validation/check_no_print_statements.py(1 hunks)src/omnibase_core/logging/core_logging.py(1 hunks)src/omnibase_core/nodes/node_effect.py(2 hunks)src/omnibase_core/nodes/node_orchestrator.py(4 hunks)src/omnibase_core/nodes/node_reducer.py(5 hunks)src/omnibase_core/utils/util_simple_fallback_logger.py(1 hunks)
✅ Files skipped from review due to trivial changes (2)
- src/omnibase_core/logging/core_logging.py
- src/omnibase_core/utils/util_simple_fallback_logger.py
🚧 Files skipped from review as they are similar to previous changes (2)
- scripts/validation/check_no_print_statements.py
- src/omnibase_core/nodes/node_effect.py
🧰 Additional context used
📓 Path-based instructions (3)
**/*.py
📄 CodeRabbit inference engine (CLAUDE.md)
**/*.py: Always use Poetry for Python package management and task execution - usepoetry runfor all Python commands (pytest, mypy, black, isort, etc.), never use pip or direct python execution
Callsuper().__init__(container)in all node class constructors - this is MANDATORY and eliminates 80+ lines of boilerplate initialization code
Always raise structured errors using ModelOnexError with appropriate EnumCoreErrorCode, never use generic Exception
Usecontainer.get_service("ProtocolName")for dependency injection - always use protocol names, never concrete class names or isinstance checks
Use @standard_error_handling decorator on methods to eliminate 6+ lines of try/catch boilerplate
Do NOT share node instances across threads - use thread-local instances or separate instances per thread for NodeCompute, NodeEffect, NodeReducer, NodeOrchestrator
Use FileRegistry for loading RuntimeHostContract YAML files - handles fail-fast error reporting with specific error codes (FILE_NOT_FOUND, CONFIGURATION_PARSE_ERROR, CONTRACT_VALIDATION_ERROR, etc.)
Use the correct container type: ModelONEXContainer for dependency injection in node constructors, ModelContainer[T] only for wrapping single values with metadata
Use EnumNodeKind for architectural classification (EFFECT, COMPUTE, REDUCER, ORCHESTRATOR) and EnumNodeType for specific implementation type (TRANSFORMER, AGGREGATOR, GATEWAY, etc.)
Format code usingpoetry run blackand sort imports usingpoetry run isortbefore committing
Lint code usingpoetry run ruff checkto detect issues and apply auto-fixes withpoetry run ruff check --fix
Files:
src/omnibase_core/nodes/node_orchestrator.pysrc/omnibase_core/nodes/node_reducer.py
src/omnibase_core/**/*.py
📄 CodeRabbit inference engine (CLAUDE.md)
src/omnibase_core/**/*.py: Achieve and maintain 100% mypy strict mode compliance with 0 errors across all source files
Achieve and maintain pyright basic mode compliance with 0 errors (targets Python 3.12)
For immutable value objects that are nested in other Pydantic models or used in parallel test execution, addfrom_attributes=Trueto ConfigDict
Use protocol-based dependency injection with container.get_service() - no isinstance checks with protocols (rely on duck typing instead)
Files:
src/omnibase_core/nodes/node_orchestrator.pysrc/omnibase_core/nodes/node_reducer.py
src/omnibase_core/nodes/**/*.py
📄 CodeRabbit inference engine (CLAUDE.md)
Import nodes from
omnibase_core.nodesusing the unified import path - useNodeCompute,NodeReducer,NodeOrchestrator,NodeEffect(NOT with 'Declarative' suffix)
Files:
src/omnibase_core/nodes/node_orchestrator.pysrc/omnibase_core/nodes/node_reducer.py
🧠 Learnings (4)
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to **/*.py : Format code using `poetry run black` and sort imports using `poetry run isort` before committing
Applied to files:
.pre-commit-config.yaml
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to **/*.py : Lint code using `poetry run ruff check` to detect issues and apply auto-fixes with `poetry run ruff check --fix`
Applied to files:
.pre-commit-config.yaml
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to **/*.py : Always use Poetry for Python package management and task execution - use `poetry run` for all Python commands (pytest, mypy, black, isort, etc.), never use pip or direct python execution
Applied to files:
.pre-commit-config.yaml
📚 Learning: 2025-12-13T20:59:19.537Z
Learnt from: CR
Repo: OmniNode-ai/omnibase_core PR: 0
File: CLAUDE.md:0-0
Timestamp: 2025-12-13T20:59:19.537Z
Learning: Applies to src/omnibase_core/**/*.py : Achieve and maintain pyright basic mode compliance with 0 errors (targets Python 3.12)
Applied to files:
.pre-commit-config.yaml
⏰ 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). (1)
- GitHub Check: Smoke Tests
🔇 Additional comments (1)
.pre-commit-config.yaml (1)
301-314: LGTM! Well-structured print statement prevention hook.The hook configuration is well-designed with:
- Appropriate exclusions for CLI tools and example files
- Clear documentation of purpose and exemption mechanism
- Consistent with other ONEX validation hooks
- Proper use of
poetry runas per coding guidelines
Address PR #187 review feedback: - Add logger initialization to docstring examples in node_orchestrator.py - Add logger initialization to docstring examples in node_reducer.py - Fix off-by-one error in validation script for separate-line quotes Users copying docstring examples will no longer encounter NameError for undefined logger variable.
The v1.1.0 contract spec requires fingerprint versions to match contract_version format with 'v' prefix (e.g., "v1.1.0:hash"). Fixed 12 contract files that had fingerprints without the 'v' prefix: - contracts/runtime/*.yaml (5 files) - examples/contracts/**/*.yaml (7 files) This resolves the CI test failure in test_fingerprint_version_matches_contract_version.
PR Review: Replace print statements with structured loggingSummaryThis PR successfully eliminates 16 print() statements across core node implementations and adds automated prevention via pre-commit hooks. The refactoring aligns with ONEX best practices for structured logging and observability. ✅ Strengths
🔍 Issues Found1. CRITICAL: Fingerprint Format Change Without Explanation
|
| Category | Rating | Notes |
|---|---|---|
| Code Quality | ⭐⭐⭐⭐ | Clean, well-structured refactoring |
| Best Practices | ⭐⭐⭐⭐⭐ | Follows ONEX patterns perfectly |
| Testing | ⭐⭐ | Missing tests for validation script |
| Security | ⭐⭐⭐⭐⭐ | No security concerns |
| Performance | ⭐⭐⭐⭐⭐ | No performance impact |
| Documentation | ⭐⭐⭐⭐⭐ | Excellent inline documentation |
🔐 Security Review
✅ No security concerns - purely refactoring logging calls
⚡ Performance Considerations
✅ No performance impact. Structured logging may be marginally slower than print(), but negligible and worth the observability benefits.
🧪 Test Coverage Review
Existing tests: 119 tests in tests/unit/nodes/ should validate that logging doesn't break functionality
Missing tests: Validation script itself (check_no_print_statements.py)
Coverage requirement: Per CLAUDE.md, minimum 60% coverage required. Validation script currently has 0% coverage.
📝 Recommendations
- MUST FIX: Clarify fingerprint format change ("v" prefix) - explain rationale or revert
- SHOULD ADD: Unit tests for validation script (at least 4-5 test cases)
- NICE TO HAVE: Document %-formatting convention for logging calls
✅ Approval Recommendation
Status:
Blockers:
- Explain/justify fingerprint format changes
Once addressed: LGTM to merge 🚀
📚 References
- ✅ Follows CLAUDE.md structured error handling patterns
- ✅ Aligns with ONEX best practices for observability
- ✅ Pre-commit integration matches existing validation patterns
⚠️ Missing test coverage per CLAUDE.md 60% requirement
Reviewed by: Claude Code Agent
Review Date: 2025-12-14
Linear: OMN-701
Address PR #137 feedback on test fixture duplication: - Add comprehensive documentation explaining fixture pattern choice - Document why factory and parameterized alternatives were rejected - Enhance load_contract_data() docstring explaining centralization - Current pattern is intentional: 2-line fixtures provide clarity
Code Review: Print Statement to Structured Logging Migration [OMN-701]✅ Strengths
|
…or [OMN-701] Add 51 unit tests covering check_no_print_statements.py validation script: - TestPrintStatementDetector (10 tests): AST-based print() detection - TestCheckDocstringPrints (10 tests): docstring example validation - TestCheckFile (7 tests): file-level checking and error handling - TestEdgeCases (12 tests): edge cases and corner scenarios - TestMainFunction (8 tests): CLI entry point behavior - TestPrintOkCommentVariations (6 tests): print-ok marker handling Addresses PR #187 feedback on missing test coverage.
There was a problem hiding this comment.
Actionable comments posted: 0
🧹 Nitpick comments (1)
tests/unit/scripts/validation/test_check_no_print_statements.py (1)
61-235: Moveastimport to module level.Multiple test methods import
astlocally (lines 71, 87, 103, 120, 140, 155, 170, 184, 204, 220). For consistency and efficiency, move this import to the module level with other imports.Apply this diff to add the import at module level:
from unittest.mock import patch +import ast import pytestThen remove all local
import aststatements from within test methods.
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
tests/unit/scripts/validation/test_check_no_print_statements.py(1 hunks)
🧰 Additional context used
📓 Path-based instructions (2)
**/*.py
📄 CodeRabbit inference engine (CLAUDE.md)
**/*.py: Always use Poetry for Python package management and task execution - usepoetry runfor all Python commands (pytest, mypy, black, isort, etc.), never use pip or direct python execution
Callsuper().__init__(container)in all node class constructors - this is MANDATORY and eliminates 80+ lines of boilerplate initialization code
Always raise structured errors using ModelOnexError with appropriate EnumCoreErrorCode, never use generic Exception
Usecontainer.get_service("ProtocolName")for dependency injection - always use protocol names, never concrete class names or isinstance checks
Use @standard_error_handling decorator on methods to eliminate 6+ lines of try/catch boilerplate
Do NOT share node instances across threads - use thread-local instances or separate instances per thread for NodeCompute, NodeEffect, NodeReducer, NodeOrchestrator
Use FileRegistry for loading RuntimeHostContract YAML files - handles fail-fast error reporting with specific error codes (FILE_NOT_FOUND, CONFIGURATION_PARSE_ERROR, CONTRACT_VALIDATION_ERROR, etc.)
Use the correct container type: ModelONEXContainer for dependency injection in node constructors, ModelContainer[T] only for wrapping single values with metadata
Use EnumNodeKind for architectural classification (EFFECT, COMPUTE, REDUCER, ORCHESTRATOR) and EnumNodeType for specific implementation type (TRANSFORMER, AGGREGATOR, GATEWAY, etc.)
Format code usingpoetry run blackand sort imports usingpoetry run isortbefore committing
Lint code usingpoetry run ruff checkto detect issues and apply auto-fixes withpoetry run ruff check --fix
Files:
tests/unit/scripts/validation/test_check_no_print_statements.py
tests/**/*.py
📄 CodeRabbit inference engine (CLAUDE.md)
tests/**/*.py: Maintain minimum 60% code coverage requirement for all tests
Use pytest markers (@pytest.mark.unit, @pytest.mark.integration, @pytest.mark.slow, @pytest.mark.smoke, @pytest.mark.performance) to categorize tests
Run tests with CI performance expectations: average 2m58s per split across 20 parallel runners, with acceptable range 2m30s-3m30s and critical threshold >4m30s
Files:
tests/unit/scripts/validation/test_check_no_print_statements.py
🧬 Code graph analysis (1)
tests/unit/scripts/validation/test_check_no_print_statements.py (1)
scripts/validation/check_no_print_statements.py (2)
PrintStatementDetector(37-90)check_docstring_prints(93-160)
⏰ 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). (2)
- GitHub Check: Smoke Tests
- GitHub Check: claude-review
🔇 Additional comments (6)
tests/unit/scripts/validation/test_check_no_print_statements.py (6)
237-387: LGTM!The docstring print detection tests are comprehensive and cover various scenarios including function, class, and module docstrings, multiline offsets, print-ok suppression, and error handling.
389-489: LGTM!The file-level checking tests comprehensively validate the integration of AST and docstring detection, along with proper error handling for missing files, syntax errors, and encoding issues.
491-622: LGTM!The edge case tests thoroughly validate unusual but valid scenarios, including empty files, shadowed builtins, nested contexts, and multiline calls. The test at lines 537-552 correctly documents the expected behavior for shadowed print variables.
624-738: LGTM!The main function tests validate the CLI entry point behavior across various scenarios, properly using mocks for sys.argv and fixtures for output capture. The tests confirm correct exit codes and output formatting.
740-826: LGTM!The print-ok comment variation tests thoroughly validate the exact string matching behavior, including whitespace handling, case sensitivity, and similar-but-different comment formats. The tests correctly document the expected matching rules.
29-55: The dynamic import usingimportlib.utilis the correct approach for this test file and is consistent with other tests intests/unit/scripts/validation/that import scripts with hyphenated filenames (e.g.,validate-all-exports.py,validate-no-direct-io.py). Python module names cannot contain hyphens, makingimportlib.util.spec_from_file_location()necessary for these scripts. Whilecheck_no_print_statements.pyhas a standard filename without hyphens and could technically use a simpler approach, maintaining consistency with the pattern used for other validation scripts is appropriate. No changes needed.
Code Review - PR #187: Replace print statements with structured loggingSummaryExcellent refactor that eliminates technical debt and enforces best practices through automation. This PR successfully addresses OMN-701 by replacing 16 print() statements across core node implementations with structured logging and adding preventative validation. Strengths1. Comprehensive Solution
2. Well-Designed Validation Script
3. Appropriate Log Levels
4. Thorough Testing
5. Clean Implementation
Code Quality Assessment
Detailed AnalysisContract Fingerprint Updates
Pre-commit Hook Integration
Exemption Pattern Usage
Potential Issues and RecommendationsMinor: Documentation Consistency
Security AnalysisNo security concerns identified:
Performance ConsiderationsPre-commit Impact:
Verdict: Performance impact negligible. Test Coverage AssessmentCoverage areas (10/10):
Verdict: Excellent test coverage for realistic scenarios. Conventional Commits ComplianceTitle: refactor(nodes): replace print statements with structured logging [OMN-701] Correct format:
Adherence to CLAUDE.md Standards
Final VerdictRecommendation: APPROVE - Merge after CI passes Rationale:
Confidence Level: High - Low-risk, high-value refactor Additional CommentsAppreciation:
Future Enhancements (Optional):
Review Metadata:
Great work, @jonahgabriel! This PR demonstrates excellent software engineering practices: identifying technical debt, implementing a comprehensive solution, and preventing future occurrences through automation. cc: Related to OMNIBASE_CORE_CODE_QUALITY_AUDIT.md - Section 2 |
…s-before-v050 Fix fingerprint version format regression introduced in main: - Remove 'v' prefix from contract fingerprints (e.g., "v1.1.0:hash" → "1.1.0:hash") - The test spec explicitly requires NO 'v' prefix per test_contract_v110_fields.py - Commit b4eb25a on main incorrectly added 'v' prefix claiming it was required - The test regex r"\d+\.\d+\.\d+" does not allow 'v' prefix Also cleaned up: - Remove empty tests/unit/models/service/ directory - Remove duplicate src/omnibase_core/models/service/ directory (canonical is services/) Merges changes from: - PR #187: Replace print statements with structured logging - PR #189: Remove global mutable state from compute_executor
Rename the `handler_kind` field to `node_archetype` across omnibase_core to align with omnibase_infra PR #187 and establish canonical vocabulary for contract-level architectural role classification. Changes: - Add EnumNodeArchetype enum (COMPUTE, EFFECT, REDUCER, ORCHESTRATOR) - Add NodeArchetypeField type alias with BeforeValidator for YAML coercion - Update ModelHandlerBehavior field: handler_kind → node_archetype - Update ModelHandlerContract validator for consistency checks - Update JSON schema with node_archetype property - Update all factory profiles to use EnumNodeArchetype enum values - Update validators, merge engine, and execution resolver - Update validation script (handler_contract_validator.py) - Update all tests (15 files), docs (4 files), and YAML examples (4 files) Breaking change: Contracts must use `node_archetype` instead of `handler_kind`. No backwards compatibility - schema rejects `handler_kind` field.
…#428) * refactor(contracts): rename handler_kind to node_archetype [OMN-1465] Rename the `handler_kind` field to `node_archetype` across omnibase_core to align with omnibase_infra PR #187 and establish canonical vocabulary for contract-level architectural role classification. Changes: - Add EnumNodeArchetype enum (COMPUTE, EFFECT, REDUCER, ORCHESTRATOR) - Add NodeArchetypeField type alias with BeforeValidator for YAML coercion - Update ModelHandlerBehavior field: handler_kind → node_archetype - Update ModelHandlerContract validator for consistency checks - Update JSON schema with node_archetype property - Update all factory profiles to use EnumNodeArchetype enum values - Update validators, merge engine, and execution resolver - Update validation script (handler_contract_validator.py) - Update all tests (15 files), docs (4 files), and YAML examples (4 files) Breaking change: Contracts must use `node_archetype` instead of `handler_kind`. No backwards compatibility - schema rejects `handler_kind` field. * refactor(contracts): simplify node_archetype comparison in validator [OMN-1465] Remove unnecessary str() cast - EnumNodeArchetype inherits from str, so enum values compare directly with strings. * chore: bump version to 0.9.2, fix schema reference [OMN-1465] - Bump version from 0.9.1 to 0.9.2 in pyproject.toml and __init__.py - Fix schema description to reference EnumNodeArchetype instead of EnumNodeKind --------- Co-authored-by: Claude (AI Assistant) <claude@omninode.ai>
Summary
Changes
Node Files Modified
node_reducer.pylogger.debug/info/warning()node_orchestrator.pylogger.debug/info/warning()node_effect.pylogger.info/error()Log Levels Applied
Prevention
scripts/validation/check_no_print_statements.pyvalidation script# print-ok: reasoncomments for CLI tools that need print()Test plan
Reference
Summary by CodeRabbit
New Features
Refactor
Chores
Tests
✏️ Tip: You can customize this high-level summary in your review settings.