@@ -103,6 +103,7 @@ You cannot use both the additive_build_content and additive_build_content_file a
103
103
def _create_whl_repos (module_ctx , pip_attr , whl_map , whl_overrides , group_map , simpleapi_cache ):
104
104
logger = repo_utils .logger (module_ctx )
105
105
python_interpreter_target = pip_attr .python_interpreter_target
106
+ is_hub_reproducible = True
106
107
107
108
# if we do not have the python_interpreter set in the attributes
108
109
# we programmatically find it.
@@ -274,6 +275,7 @@ def _create_whl_repos(module_ctx, pip_attr, whl_map, whl_overrides, group_map, s
274
275
logger .debug (lambda : "Selected: {}" .format (distribution ))
275
276
276
277
if distribution :
278
+ is_hub_reproducible = False
277
279
whl_library_args ["requirement" ] = requirement .srcs .requirement
278
280
whl_library_args ["urls" ] = [distribution .url ]
279
281
whl_library_args ["sha256" ] = distribution .sha256
@@ -303,6 +305,8 @@ def _create_whl_repos(module_ctx, pip_attr, whl_map, whl_overrides, group_map, s
303
305
),
304
306
)
305
307
308
+ return is_hub_reproducible
309
+
306
310
def _pip_impl (module_ctx ):
307
311
"""Implementation of a class tag that creates the pip hub and corresponding pip spoke whl repositories.
308
312
@@ -412,6 +416,7 @@ def _pip_impl(module_ctx):
412
416
hub_group_map = {}
413
417
414
418
simpleapi_cache = {}
419
+ is_extension_reproducible = True
415
420
416
421
for mod in module_ctx .modules :
417
422
for pip_attr in mod .tags .parse :
@@ -448,7 +453,8 @@ def _pip_impl(module_ctx):
448
453
else :
449
454
pip_hub_map [pip_attr .hub_name ].python_versions .append (pip_attr .python_version )
450
455
451
- _create_whl_repos (module_ctx , pip_attr , hub_whl_map , whl_overrides , hub_group_map , simpleapi_cache )
456
+ is_hub_reproducible = _create_whl_repos (module_ctx , pip_attr , hub_whl_map , whl_overrides , hub_group_map , simpleapi_cache )
457
+ is_extension_reproducible = is_extension_reproducible and is_hub_reproducible
452
458
453
459
for hub_name , whl_map in hub_whl_map .items ():
454
460
pip_repository (
@@ -462,7 +468,34 @@ def _pip_impl(module_ctx):
462
468
groups = hub_group_map .get (hub_name ),
463
469
)
464
470
465
- def _pip_parse_ext_attrs ():
471
+ if bazel_features .external_deps .extension_metadata_has_reproducible :
472
+ # If we are not using the `experimental_index_url feature, the extension is fully
473
+ # deterministic and we don't need to create a lock entry for it.
474
+ #
475
+ # In order to be able to dogfood the `experimental_index_url` feature before it gets
476
+ # stabilized, we have created the `_pip_non_reproducible` function, that will result
477
+ # in extra entries in the lock file.
478
+ return module_ctx .extension_metadata (reproducible = is_extension_reproducible )
479
+ else :
480
+ return None
481
+
482
+ def _pip_non_reproducible (module_ctx ):
483
+ _pip_impl (module_ctx )
484
+
485
+ # We default to calling the PyPI index and that will go into the
486
+ # MODULE.bazel.lock file, hence return nothing here.
487
+ return None
488
+
489
+ def _pip_parse_ext_attrs (** kwargs ):
490
+ """Get the attributes for the pip extension.
491
+
492
+ Args:
493
+ **kwargs: A kwarg for setting defaults for the specific attributes. The
494
+ key is expected to be the same as the attribute key.
495
+
496
+ Returns:
497
+ A dict of attributes.
498
+ """
466
499
attrs = dict ({
467
500
"experimental_extra_index_urls" : attr .string_list (
468
501
doc = """\
@@ -477,6 +510,7 @@ This is equivalent to `--extra-index-urls` `pip` option.
477
510
default = [],
478
511
),
479
512
"experimental_index_url" : attr .string (
513
+ default = kwargs .get ("experimental_index_url" , "" ),
480
514
doc = """\
481
515
The index URL to use for downloading wheels using bazel downloader. This value is going
482
516
to be subject to `envsubst` substitutions if necessary.
@@ -661,17 +695,6 @@ Apply any overrides (e.g. patches) to a given Python distribution defined by
661
695
other tags in this extension.""" ,
662
696
)
663
697
664
- def _extension_extra_args ():
665
- args = {}
666
-
667
- if bazel_features .external_deps .module_extension_has_os_arch_dependent :
668
- args = args | {
669
- "arch_dependent" : True ,
670
- "os_dependent" : True ,
671
- }
672
-
673
- return args
674
-
675
698
pip = module_extension (
676
699
doc = """\
677
700
This extension is used to make dependencies from pip available.
@@ -714,7 +737,56 @@ extension.
714
737
""" ,
715
738
),
716
739
},
717
- ** _extension_extra_args ()
740
+ )
741
+
742
+ pip_internal = module_extension (
743
+ doc = """\
744
+ This extension is used to make dependencies from pypi available.
745
+
746
+ For now this is intended to be used internally so that usage of the `pip`
747
+ extension in `rules_python` does not affect the evaluations of the extension
748
+ for the consumers.
749
+
750
+ pip.parse:
751
+ To use, call `pip.parse()` and specify `hub_name` and your requirements file.
752
+ Dependencies will be downloaded and made available in a repo named after the
753
+ `hub_name` argument.
754
+
755
+ Each `pip.parse()` call configures a particular Python version. Multiple calls
756
+ can be made to configure different Python versions, and will be grouped by
757
+ the `hub_name` argument. This allows the same logical name, e.g. `@pypi//numpy`
758
+ to automatically resolve to different, Python version-specific, libraries.
759
+
760
+ pip.whl_mods:
761
+ This tag class is used to help create JSON files to describe modifications to
762
+ the BUILD files for wheels.
763
+ """ ,
764
+ implementation = _pip_non_reproducible ,
765
+ tag_classes = {
766
+ "override" : _override_tag ,
767
+ "parse" : tag_class (
768
+ attrs = _pip_parse_ext_attrs (
769
+ experimental_index_url = "https://pypi.org/simple" ,
770
+ ),
771
+ doc = """\
772
+ This tag class is used to create a pypi hub and all of the spokes that are part of that hub.
773
+ This tag class reuses most of the pypi attributes that are found in
774
+ @rules_python//python/pip_install:pip_repository.bzl.
775
+ The exception is it does not use the arg 'repo_prefix'. We set the repository
776
+ prefix for the user and the alias arg is always True in bzlmod.
777
+ """ ,
778
+ ),
779
+ "whl_mods" : tag_class (
780
+ attrs = _whl_mod_attrs (),
781
+ doc = """\
782
+ This tag class is used to create JSON file that are used when calling wheel_builder.py. These
783
+ JSON files contain instructions on how to modify a wheel's project. Each of the attributes
784
+ create different modifications based on the type of attribute. Previously to bzlmod these
785
+ JSON files where referred to as annotations, and were renamed to whl_modifications in this
786
+ extension.
787
+ """ ,
788
+ ),
789
+ },
718
790
)
719
791
720
792
def _whl_mods_repo_impl (rctx ):
0 commit comments