Skip to content

refactor: modernize imports and use pathlib APIs - #381

Merged
jan-janssen merged 6 commits into
pyiron:mainfrom
inquilabee:refactor/modernize-imports-and-pathlib
Jul 29, 2026
Merged

refactor: modernize imports and use pathlib APIs#381
jan-janssen merged 6 commits into
pyiron:mainfrom
inquilabee:refactor/modernize-imports-and-pathlib

Conversation

@inquilabee

@inquilabee inquilabee commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

Summary

Repo health: 20/100

Our analysis found ~720 format/lint tidy opportunities and about 183 refactoring opportunities across the reviewed scope. Security scans flagged one subprocess call with shell=True in compatibility/file.py (bandit B602); code duplication is low (~0.7% in Python modules per jscpd); cyclomatic complexity P95 slightly exceeds the configured ceiling (radon); about 183 structural refactor suggestions remain (repeated strings, class-local helpers, test-only API surface).

This pull request is a sample of those findings — 19 files, ~141 focused line changes — not a full format pass or refactor cleanup.

What you are doing right

  • No secrets detected in scope (gitleaks).
  • Code duplication is very low (~0.7% duplicated lines in Python modules per jscpd).
  • Strong CI matrix (Python 3.9–3.14) with black, mypy, coverage, and multi-platform unittest jobs.
  • Modern PEP 621 + hatchling packaging with comprehensive scientific test suite (153 tests).
  • Clear separation between structure I/O, output parsing, and compatibility layers.

What you could improve

  • Security: subprocess is invoked with shell=True in compatibility/file.py:252 — consider argv list form if the command string is not strictly required. (follow-up)
  • Maintainability / complexity: radon reported P95 cyclomatic complexity of 8.0 (ceiling 7) across scanned functions — mostly in output parsing paths. (follow-up)
  • Refactoring: About 183 refactor check --strict suggestions remain — e.g. extract repeated 'Structure not set' string constant in structure.py and move class-local helpers to @staticmethod. (follow-up)
  • Dead code: vulture flagged an unused lammps import in tests/test_compatibility_integration.py. (defer — integration test fixture)
  • Dependencies: deptry flagged tomlkit used in .ci_support/check.py but not declared in pyproject.toml. (defer — CI script only)
  • Lint / style: Prefer pathlib.Path over os.path / open() for file existence and reads. (included in example PR)
  • Lint / style: Modernize typing.Union to X | Y and import Callable from collections.abc. (included in example PR)
  • Lint / style: Simplify redundant else branches after early returns and use dict.fromkeys where applicable. (included in example PR)

Changes

  • src/lammpsparser/_version.py — modernize VERSION_TUPLE type hint to PEP 604 syntax.
  • src/lammpsparser/compatibility/calculate.py — remove redundant else after raise; quote cast() type expression.
  • src/lammpsparser/compatibility/file.py — use pathlib.Path.mkdir() and Path.open() for LAMMPS input file writes.
  • src/lammpsparser/compatibility/structure.py — use dict.fromkeys for charge dict; quote cast() type; tidy comments.
  • src/lammpsparser/output.py — import Callable from collections.abc; use Path.is_file() for dump detection.
  • src/lammpsparser/output_raw.py — pathlib and import modernizations.
  • src/lammpsparser/potential.py — import sorting and minor style cleanups.
  • src/lammpsparser/structure.py — import and style tidy-ups.
  • src/lammpsparser/units.py — import modernizations.
  • tests/test_*.py (10 files) — align test imports and pathlib usage with source changes.

Review summary produced with ShipGate — a policy-first quality orchestrator that runs linters, formatters, security scanners, and refactor checks from one catalog. This PR used check + refactor check --strict to find issues; docs.

Summary by CodeRabbit

  • Refactor

    • Improved filesystem handling for reading, writing, directory creation, and file detection.
    • Simplified internal control flow without changing expected behavior.
    • Preserved potential validation, unit conversion, structure generation, and output parsing behavior.
  • Tests

    • Updated filesystem-related tests and test setup to align with the improved file handling.
    • Refined test organization and formatting without changing coverage or assertions.

Prefer pathlib.Path over os.path/open in compatibility and output
modules, modernize typing imports (PEP 604, collections.abc), and
simplify redundant else branches. black --check and unittest suite
pass locally (153 tests).
@inquilabee
inquilabee requested a review from jan-janssen as a code owner July 29, 2026 09:58
@coderabbitai

coderabbitai Bot commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

The PR standardizes filesystem operations on pathlib and simplifies control flow in compatibility, output, potential, structure, and unit-conversion modules. Tests update corresponding file handling, imports, setup, and formatting without changing assertions or public interfaces.

Changes

Parser modernization

Layer / File(s) Summary
Pathlib filesystem migration
src/lammpsparser/compatibility/file.py, src/lammpsparser/output.py, src/lammpsparser/output_raw.py, src/lammpsparser/structure.py, tests/...
Directory creation, existence checks, and file reads/writes use pathlib across production code and tests.
Compatibility and conversion cleanup
src/lammpsparser/compatibility/calculate.py, src/lammpsparser/compatibility/file.py, src/lammpsparser/compatibility/structure.py, src/lammpsparser/units.py, tests/...
Pressure handling, input modification, charge initialization, unknown-unit fallback, and related test formatting are simplified while preserving described behavior.
Potential lookup and validation cleanup
src/lammpsparser/potential.py, tests/test_potential.py
Potential lookup and resource checks use Path, attribute fallback control flow is simplified, and potential input validation is restructured with the same accepted input categories and exception conditions.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Possibly related PRs

Suggested reviewers: jan-janssen

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 21.05% 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
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately captures the main refactor: import cleanup and broader pathlib adoption.
✨ Finishing Touches 💡 1
🛠️ Fix failing CI checks 💡
  • Fix failing CI checks
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

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

@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

🧹 Nitpick comments (1)
src/lammpsparser/units.py (1)

240-244: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Add stacklevel to warnings.warn.

Without stacklevel=2, the warning will point at this internal line rather than the caller's code, making it harder for users to locate the offending call.

♻️ Proposed fix
         warnings.warn(
             message="Warning: Couldn't determine the LAMMPS to pyiron unit conversion type of quantity "
-            f"{label}. Returning un-normalized quantity"
+            f"{label}. Returning un-normalized quantity",
+            stacklevel=2,
         )
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/lammpsparser/units.py` around lines 240 - 244, The warnings.warn call in
the unit-conversion fallback should specify stacklevel=2 so the warning points
to the caller rather than the internal parser line. Update this warning
invocation while preserving its message and the subsequent np.array(array)
return.

Source: Linters/SAST tools

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/lammpsparser/output.py`:
- Around line 4-7: Complete the pathlib migration in parse_lammps_output by
replacing the remaining os.path.join calls with pathlib.Path-based path
construction and string conversion, preserving the existing working_directory
and filename values; do not leave unresolved os references after removing the
import.

---

Nitpick comments:
In `@src/lammpsparser/units.py`:
- Around line 240-244: The warnings.warn call in the unit-conversion fallback
should specify stacklevel=2 so the warning points to the caller rather than the
internal parser line. Update this warning invocation while preserving its
message and the subsequent np.array(array) return.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: dcede283-5096-4b24-8430-d3babe0aceff

📥 Commits

Reviewing files that changed from the base of the PR and between 3f79f1b and c8a804c.

📒 Files selected for processing (19)
  • src/lammpsparser/_version.py
  • src/lammpsparser/compatibility/calculate.py
  • src/lammpsparser/compatibility/file.py
  • src/lammpsparser/compatibility/structure.py
  • src/lammpsparser/output.py
  • src/lammpsparser/output_raw.py
  • src/lammpsparser/potential.py
  • src/lammpsparser/structure.py
  • src/lammpsparser/units.py
  • tests/test_compatibility_calculate.py
  • tests/test_compatibility_file.py
  • tests/test_compatibility_integration.py
  • tests/test_compatibility_output_structure.py
  • tests/test_compatibility_structure.py
  • tests/test_output.py
  • tests/test_output_raw.py
  • tests/test_potential.py
  • tests/test_structure.py
  • tests/test_units.py

Comment thread src/lammpsparser/output.py
@codecov

codecov Bot commented Jul 29, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 98.69%. Comparing base (3f79f1b) to head (e099c90).

Additional details and impacted files
@@           Coverage Diff           @@
##             main     #381   +/-   ##
=======================================
  Coverage   98.68%   98.69%           
=======================================
  Files          13       13           
  Lines        1219     1224    +5     
=======================================
+ Hits         1203     1208    +5     
  Misses         16       16           

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@jan-janssen
jan-janssen merged commit fdd49b4 into pyiron:main Jul 29, 2026
62 of 66 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants