fix: declare PyInfo as provided by test/binary/library (#2777)

Currently, the rules don't advertise the PyInfo provider through the
provides argument
to the rule function. This means that aspects that want to consume
PyInfo can't use
`required_providers` to restrict themselves to the Python rules, and
instead have to
apply to all rules.

To fix, add PyInfo to the provides arg of the rules.

Fixes https://github.com/bazel-contrib/rules_python/issues/2506

---------

Co-authored-by: Richard Levasseur <rlevasseur@google.com>
Co-authored-by: Richard Levasseur <richardlev@gmail.com>
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 1378853..cad074e 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -47,6 +47,28 @@
 END_UNRELEASED_TEMPLATE
 -->
 
+{#v0-0-0}
+## Unreleased
+
+[0.0.0]: https://github.com/bazel-contrib/rules_python/releases/tag/0.0.0
+
+{#v0-0-0-changed}
+### Changed
+* Nothing changed.
+
+{#v0-0-0-fixed}
+### Fixed
+* (rules) PyInfo provider is now advertised by py_test, py_binary, and py_library;
+  this allows aspects using required_providers to function correctly.
+  ([#2506](https://github.com/bazel-contrib/rules_python/issues/2506)).
+
+{#v0-0-0-added}
+### Added
+* Nothing added.
+
+{#v0-0-0-removed}
+### Removed
+* Nothing removed.
 
 {#1-4-0}
 ## [1.4.0] - 2025-04-19
diff --git a/python/private/py_executable.bzl b/python/private/py_executable.bzl
index dd3ad86..b4cda21 100644
--- a/python/private/py_executable.bzl
+++ b/python/private/py_executable.bzl
@@ -1854,6 +1854,8 @@
     """
     return create_executable_rule_builder().build()
 
+_MaybeBuiltinPyInfo = [BuiltinPyInfo] if BuiltinPyInfo != None else []
+
 # NOTE: Exported publicly
 def create_executable_rule_builder(implementation, **kwargs):
     """Create a rule builder for an executable Python program.
@@ -1877,7 +1879,7 @@
         attrs = EXECUTABLE_ATTRS,
         exec_groups = dict(REQUIRED_EXEC_GROUP_BUILDERS),  # Mutable copy
         fragments = ["py", "bazel_py"],
-        provides = [PyExecutableInfo],
+        provides = [PyExecutableInfo, PyInfo] + _MaybeBuiltinPyInfo,
         toolchains = [
             ruleb.ToolchainType(TOOLCHAIN_TYPE),
             ruleb.ToolchainType(EXEC_TOOLS_TOOLCHAIN_TYPE, mandatory = False),
diff --git a/python/private/py_library.bzl b/python/private/py_library.bzl
index 6b5882d..bf0c254 100644
--- a/python/private/py_library.bzl
+++ b/python/private/py_library.bzl
@@ -43,7 +43,9 @@
 load(":flags.bzl", "AddSrcsToRunfilesFlag", "PrecompileFlag", "VenvsSitePackages")
 load(":precompile.bzl", "maybe_precompile")
 load(":py_cc_link_params_info.bzl", "PyCcLinkParamsInfo")
+load(":py_info.bzl", "PyInfo")
 load(":py_internal.bzl", "py_internal")
+load(":reexports.bzl", "BuiltinPyInfo")
 load(":rule_builders.bzl", "ruleb")
 load(
     ":toolchain_types.bzl",
@@ -299,6 +301,8 @@
     else:
         return short_path
 
+_MaybeBuiltinPyInfo = [BuiltinPyInfo] if BuiltinPyInfo != None else []
+
 # NOTE: Exported publicaly
 def create_py_library_rule_builder():
     """Create a rule builder for a py_library.
@@ -319,6 +323,7 @@
         exec_groups = dict(REQUIRED_EXEC_GROUP_BUILDERS),
         attrs = LIBRARY_ATTRS,
         fragments = ["py"],
+        provides = [PyCcLinkParamsInfo, PyInfo] + _MaybeBuiltinPyInfo,
         toolchains = [
             ruleb.ToolchainType(TOOLCHAIN_TYPE, mandatory = False),
             ruleb.ToolchainType(EXEC_TOOLS_TOOLCHAIN_TYPE, mandatory = False),