Skip to content

Comments

[CI][Enhancement] Add Pytest in unit test#154

Merged
RMLYC merged 13 commits intotile-ai:mainfrom
RMLYC:lyc/add_pytest_in_mha_gqa
Feb 10, 2026
Merged

[CI][Enhancement] Add Pytest in unit test#154
RMLYC merged 13 commits intotile-ai:mainfrom
RMLYC:lyc/add_pytest_in_mha_gqa

Conversation

@RMLYC
Copy link
Collaborator

@RMLYC RMLYC commented Jan 23, 2026

Description

  1. Refactor the current testing framework using the pytest framework;
  2. Remove profile testing in ci.yml, retaining only unit tests;
  3. Fix the precision thresholds for some test cases;
  4. Other minor bug fixes.
  5. '@py_assert1' in test_deepseek_nsa_cmp_fwd.py will be fixed in [Fix][NSA] Fixed a bug in pytest parameter passing in test_deepseek_nsa_cmp_fwd. #171

Type of Change

  • Infrastructure/CI

Checklist

  • I have run pre-commit run --all-files and fixed all linting issues.
  • I have verified that my changes pass local unit tests.

@RMLYC RMLYC requested a review from a team January 23, 2026 07:00
@RMLYC RMLYC marked this pull request as draft January 23, 2026 07:00
@gemini-code-assist
Copy link
Contributor

Summary of Changes

Hello @RMLYC, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

This pull request significantly enhances the unit testing framework for MultiHeadAttention and GroupQueryAttention operations by integrating Pytest's parameterization capabilities. This allows for more comprehensive and flexible testing across various configurations and data types, improving the robustness of these critical components and streamlining the testing process.

Highlights

  • Pytest Parameterization for GroupQueryAttention (GQA): The unit tests for GroupQueryAttention's forward (test_gqa_fwd) and backward (test_gqa_bwd) passes in tests/ops/test_gqa.py have been refactored to utilize pytest.mark.parametrize. This allows for running the same test function with multiple sets of input parameters, significantly expanding test coverage with concise code.
  • Pytest Parameterization for MultiHeadAttention (MHA): Similarly, the forward (test_mha_fwd) and backward (test_mha_bwd) unit tests for MultiHeadAttention in tests/ops/test_mha.py now leverage pytest.mark.parametrize. This introduces new test configurations, including different batch sizes, sequence lengths, head counts, dimensions, causality settings, and data types (float16, bfloat16).
  • Enhanced Test Logging in MHA: Print statements within the MHA tests (test_mha_fwd and test_mha_bwd) have been updated to output the specific parameters for each test run. This provides clearer context and aids in debugging when tests are executed.
  • Removal of Benchmarking Calls in MHA Tests: The explicit benchmark.profile calls have been removed from the MHA unit test functions (test_mha_fwd and test_mha_bwd). This change streamlines the unit test execution, focusing solely on correctness rather than performance profiling within these specific tests.

🧠 New Feature in Public Preview: You can now enable Memory to help Gemini Code Assist learn from your team's feedback. This makes future code reviews more consistent and personalized to your project's style. Click here to enable Memory in your admin console.

Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

Copy link
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

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

Code Review

This pull request is a great enhancement, introducing pytest to the unit tests for MultiHeadAttention and GroupQueryAttention, which will improve the testing structure and CI process. The use of pytest.mark.parametrize makes the tests cleaner and easier to extend.

I've noticed one inconsistency: the benchmark.profile() calls have been removed from tests/ops/test_mha.py, which is good for speeding up unit tests, but they remain in tests/ops/test_gqa.py. It would be best to remove them from test_gqa.py as well for consistency.

I have also left a few specific comments in tests/ops/test_mha.py regarding missing type hints and test case coverage. Addressing these will improve code quality and maintainability.

@RMLYC RMLYC force-pushed the lyc/add_pytest_in_mha_gqa branch from d62c67c to a1c403e Compare February 4, 2026 13:15
@RMLYC RMLYC force-pushed the lyc/add_pytest_in_mha_gqa branch from 477f628 to e5c7822 Compare February 6, 2026 06:15
@RMLYC RMLYC marked this pull request as ready for review February 9, 2026 07:45
@RMLYC
Copy link
Collaborator Author

RMLYC commented Feb 9, 2026

/gemini summary

@gemini-code-assist
Copy link
Contributor

Summary of Changes

This pull request significantly refactors the project's unit testing infrastructure by migrating a large number of existing tests to the pytest framework. The core change involves replacing custom test execution logic with pytest.mark.parametrize for defining test cases, which substantially enhances test coverage and maintainability. A new conftest.py file centralizes global test configurations, and the CI script has been updated to reflect these changes, ensuring a more robust and standardized testing pipeline for critical components like attention mechanisms.

Highlights

  • Test Framework Migration: Numerous unit tests have been transitioned from custom argparse-based execution to the pytest framework, utilizing pytest.mark.parametrize for efficient and comprehensive test case definition across various modules.
  • Centralized Test Setup: A new tests/conftest.py file has been introduced to centralize global test setup, specifically for setting PyTorch random seeds, ensuring reproducibility and consistency across all Pytest-driven tests.
  • CI Script Update: The tests/ci_test.sh script has been modified to execute tests using python -m pytest, streamlining the continuous integration process and aligning with the new standardized testing methodology.
  • Code Cleanup and Standardization: Redundant argparse imports, str2dtype utility calls, and manual test execution blocks (if __name__ == "__main__":) have been removed from individual test files, leading to cleaner, more consistent, and maintainable test code.
  • Enhanced Test Coverage for Attention Mechanisms: Test configurations for MultiHeadAttention (MHA) and GroupQueryAttention (GQA) operations have been expanded through parameterization, allowing for broader validation across various input shapes, data types, and causal settings.

🧠 New Feature in Public Preview: You can now enable Memory to help Gemini Code Assist learn from your team's feedback. This makes future code reviews more consistent and personalized to your project's style. Click here to enable Memory in your admin console.

Changelog
  • benchmarks/flash_attn/mha.py
    • Removed a commented-out IPython embed line.
  • tests/ci_test.sh
    • Modified logging output by removing tee -a "$LOG_FILE" from several echo commands to simplify log redirection.
    • Updated test execution logic to use python -m pytest "$test_file" instead of direct python "$test_file", integrating Pytest into the CI pipeline.
    • Adjusted the path in the 'No test files found' message for accuracy.
  • tests/conftest.py
    • Added a new file to set a global torch.manual_seed and torch.cuda.manual_seed_all for consistent test reproducibility across all Pytest runs.
  • tests/functions/test_deepseek_dsa_decode_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_deepseek_mla_decode_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_fp8_lighting_indexer_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse imports and str2dtype utility.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
    • Removed a duplicate test function and associated manual benchmark checks.
  • tests/functions/test_fp8_quant.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Replaced manual test execution calls in if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_gqa_decode_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_gqa_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_grouped_gemm_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_matmul_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_mha_decode_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_mha_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/functions/test_topk_selector_func.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/layers/test_gqa_decode_layer.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/layers/test_gqa_layer.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/layers/test_grouped_gemm_layer.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/layers/test_linear.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/layers/test_mha_decode_layer.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/layers/test_mha_layer.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_deepseek_dsa_decode.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_deepseek_mla_decode.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_deepseek_nsa_cmp_fwd.py
    • Removed pytest.fixture(autouse=True) as global setup is now handled by tests/conftest.py.
    • Replaced manual test execution calls in if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_deepseek_nsa_fwd.py
    • Removed pytest.fixture(autouse=True) as global setup is now handled by tests/conftest.py.
    • Replaced manual test execution calls in if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_deepseek_nsa_gqa_window_sliding.py
    • Removed pytest.fixture(autouse=True) as global setup is now handled by tests/conftest.py.
    • Adjusted atol and rtol parameters in benchmark.check for more robust comparisons.
    • Replaced manual test execution calls in if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_deepseek_nsa_topk.py
    • Removed pytest.fixture(autouse=True) as global setup is now handled by tests/conftest.py.
    • Replaced manual test execution calls in if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_fp8_lighting_indexer.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_fp8_quant.py
    • Replaced manual test execution calls in if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_gemm.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_gqa.py
    • Converted test_gqa_fwd and test_gqa_bwd functions to use pytest.mark.parametrize for defining test cases.
    • Adjusted atol parameter in benchmark.check for both forward and backward tests.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_gqa_decode.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_gqa_decode_paged.py
    • Removed pytest.fixture(autouse=True) as global setup is now handled by tests/conftest.py.
    • Added if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])) for direct execution via pytest.
  • tests/ops/test_gqa_decode_paged_legacy.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Added explicit torch.manual_seed call within the test function for local reproducibility.
    • Adjusted atol and rtol parameters in benchmark.check for more robust comparisons.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_grouped_gemm.py
    • Converted multiple test_grouped_gemm_* functions to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_mean_pooling_ops.py
    • Replaced manual test execution calls in if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_mha.py
    • Converted test_mha_fwd and test_mha_bwd functions to use pytest.mark.parametrize for defining test cases.
    • Adjusted atol parameter in benchmark.check for both forward and backward tests.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_mha_decode.py
    • Removed explicit torch.manual_seed calls as global setup is now handled by tests/conftest.py.
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_mha_decode_paged.py
    • Removed pytest.fixture(autouse=True) as global setup is now handled by tests/conftest.py.
    • Added if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])) for direct execution via pytest.
  • tests/ops/test_mha_decode_paged_legacy.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Adjusted atol and rtol parameters in benchmark.check for more robust comparisons.
    • Removed argparse and str2dtype imports.
    • Replaced manual test execution block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/ops/test_mha_decode_pytest.py
    • Removed the file, as its functionality was integrated into tests/ops/test_mha_decode.py.
  • tests/ops/test_mhc_post.py
    • Removed pytest.fixture(autouse=True) as global setup is now handled by tests/conftest.py.
    • Added if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])) for direct execution via pytest.
  • tests/ops/test_mhc_pre.py
    • Removed pytest.fixture(autouse=True) as global setup is now handled by tests/conftest.py.
    • Added if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])) for direct execution via pytest.
  • tests/ops/test_topk_selector.py
    • Replaced manual test execution calls in if __name__ == "__main__": block with sys.exit(pytest.main([__file__, "-vvs"])).
  • tests/test_autotune.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Added pytest and torch imports.
  • tests/test_compile.py
    • Converted test function to use pytest.mark.parametrize for defining test cases.
    • Added pytest import.
    • Adjusted atol parameter in benchmark.check for compatibility with compiled operations.
  • tests/test_gemm_torch.py
    • Converted benchmark_pytorch_gemm and benchmark_cublas_gemm functions to pytest.mark.parametrize tests, renamed to test_pytorch_gemm and test_cublas_gemm respectively.
    • Updated the if __name__ == "__main__": block to call the new Pytest-compatible test functions.
  • tests/test_gemm_triton.py
    • Converted benchmark_triton_gemm_fp16 and verify_triton_gemm_fp16 functions to pytest.mark.parametrize tests, renamed to test_benchmark_triton_gemm_fp16 and test_verify_triton_gemm_fp16 respectively.
    • Updated the if __name__ == "__main__": block to call the new Pytest-compatible test functions.
  • tests/test_grouped_gemm_torch.py
    • Converted test_all_grouped_gemm function to use pytest.mark.parametrize for defining test cases.
    • Updated the if __name__ == "__main__": block to call the new Pytest-compatible test function with parameters.
  • tests/test_grouped_gemm_triton.py
    • Converted multiple test_grouped_gemm_* functions to use pytest.mark.parametrize for defining test cases.
Ignored Files
  • Ignored by pattern: .github/workflows/** (1)
    • .github/workflows/ci.yml
Activity
  • An initial summary of the pull request was provided by gemini-code-assist[bot].
  • gemini-code-assist[bot] provided review comments suggesting the addition of type hints to test_mha_fwd and test_mha_bwd functions in tests/ops/test_mha.py.
  • gemini-code-assist[bot] also noted a missing test case in test_mha_bwd for better test coverage.
  • The author, RMLYC, requested a new summary of the pull request.

@gemini-code-assist
Copy link
Contributor

It looks like you might have intended to use the /gemini summary command. There was a small typo in your last comment. I've already provided a summary in comment #3. Please let me know if you need anything else!

zhen8838
zhen8838 previously approved these changes Feb 9, 2026
Copy link
Collaborator

@superAngGao superAngGao left a comment

Choose a reason for hiding this comment

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

Cool! Thank you a lot for your contributions!

Copy link
Collaborator

@zhen8838 zhen8838 left a comment

Choose a reason for hiding this comment

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

Great Job

@RMLYC RMLYC changed the title [CI][Enhancement] Add Pytest in MultiHeadAttention and GroupQueryAttention unit test [CI][Enhancement] Add Pytest in unit test Feb 10, 2026
@RMLYC RMLYC merged commit db9b214 into tile-ai:main Feb 10, 2026
2 of 3 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.

4 participants