@@ -242,8 +242,30 @@ def showcase_library(
242242 include_service_yaml = True ,
243243 retry_config = True ,
244244 rest_async_io_enabled = False ,
245+ install_async_rest_extra = False ,
245246):
246- """Install the generated library into the session for showcase tests."""
247+ """Install the generated library into the session for showcase tests.
248+
249+ Args:
250+ session: The nox session object.
251+ templates (str): The template directory to use for code generation.
252+ Defaults to "DEFAULT".
253+ other_opts (typing.Iterable[str]): Additional options passed to
254+ `--python_gapic_opt` during code generation.
255+ include_service_yaml (bool): Whether to download and pass
256+ `showcase_v1beta1.yaml` to the generator.
257+ retry_config (bool): Whether to download and pass
258+ `showcase_grpc_service_config.json` to the generator.
259+ rest_async_io_enabled (bool): Whether to enable the experimental
260+ `rest_async_io_enabled` setting in `showcase_v1beta1.yaml` so
261+ `rest_asyncio` transports are generated for all services. When True,
262+ the `[async_rest]` extra is also installed.
263+ install_async_rest_extra (bool): Whether to install the generated
264+ library with the `[async_rest]` extra and its corresponding
265+ `constraints-{python}-async-rest.txt` file even when
266+ `rest_async_io_enabled` is False in `showcase_v1beta1.yaml` (e.g.,
267+ for services with resumable upload methods).
268+ """
247269
248270 session .log ("-" * 70 )
249271 session .log ("Note: Showcase must be running for these tests to work." )
@@ -371,19 +393,19 @@ def showcase_library(
371393 constraints_path = str (
372394 f"{ tmp_dir } /testing/constraints-{ session .python } .txt"
373395 )
374- async_rest_constraints_path = str (
375- f"{ tmp_dir } /testing/constraints-{ session .python } -async-rest.txt"
376- )
377- if os .path .exists (async_rest_constraints_path ):
378- # use async-rest constraints if available
379- constraints_path = async_rest_constraints_path
380- else :
381- session .log (
382- f"{ async_rest_constraints_path } not found. Using base constraints file"
396+ extras = ""
397+ if rest_async_io_enabled or install_async_rest_extra :
398+ async_rest_constraints_path = str (
399+ f"{ tmp_dir } /testing/constraints-{ session .python } -async-rest.txt"
383400 )
384- # Showcase protos include `resumable_media.proto`
385- # Include the `async_rest` extra.
386- extras = "[async_rest]"
401+ if os .path .exists (async_rest_constraints_path ):
402+ # use async-rest constraints if available
403+ constraints_path = async_rest_constraints_path
404+ extras = "[async_rest]"
405+ else :
406+ session .log (
407+ f"{ async_rest_constraints_path } not found. Using base constraints file"
408+ )
387409 session .install ("-e" , f"{ tmp_dir } { extras } " , "-r" , constraints_path )
388410 else :
389411 # The ads templates do not have constraints files.
@@ -395,8 +417,10 @@ def showcase_library(
395417
396418
397419@nox .session (python = ALL_PYTHON )
420+ @nox .parametrize ("install_async_rest_extra" , [False , True ])
398421def showcase (
399422 session ,
423+ install_async_rest_extra = False ,
400424 templates = "DEFAULT" ,
401425 other_opts : typing .Iterable [str ] = (),
402426 env : typing .Optional [typing .Dict [str , str ]] = {},
@@ -407,7 +431,12 @@ def showcase(
407431 (useful for local testing and canary validation).
408432 """
409433
410- with showcase_library (session , templates = templates , other_opts = other_opts ):
434+ with showcase_library (
435+ session ,
436+ templates = templates ,
437+ other_opts = other_opts ,
438+ install_async_rest_extra = install_async_rest_extra ,
439+ ):
411440 # When opt-in environment variable is set (e.g. in canary CI or local testing),
412441 # install the local google-api-core package from source.
413442 if os .getenv ("INSTALL_LOCAL_CORE" ) == "true" :
@@ -535,7 +564,26 @@ def showcase_pqc(
535564 )
536565
537566
538- def run_showcase_unit_tests (session , fail_under = 100 , rest_async_io_enabled = False ):
567+ def run_showcase_unit_tests (
568+ session ,
569+ fail_under = 100 ,
570+ rest_async_io_enabled = False ,
571+ install_async_rest_extra = False ,
572+ ):
573+ """Run the generated Showcase unit test suite with coverage verification.
574+
575+ Args:
576+ session: The nox session object.
577+ fail_under (int): Minimum required test coverage percentage.
578+ Defaults to 100.
579+ rest_async_io_enabled (bool): Whether `rest_async_io_enabled` was enabled
580+ in `showcase_v1beta1.yaml` during code generation.
581+ install_async_rest_extra (bool): Whether the library was installed with
582+ the `[async_rest]` extra. When both `rest_async_io_enabled` and
583+ `install_async_rest_extra` are False, `**/rest_asyncio.py` is omitted
584+ from coverage since optional `async_rest` dependencies are not
585+ installed.
586+ """
539587 session .install (
540588 "coverage" ,
541589 "pytest" ,
@@ -546,6 +594,20 @@ def run_showcase_unit_tests(session, fail_under=100, rest_async_io_enabled=False
546594 # Freeze and print python environment package versions
547595 session .run ("python" , "-m" , "pip" , "freeze" )
548596
597+ if (
598+ not rest_async_io_enabled
599+ and not install_async_rest_extra
600+ and path .exists (".coveragerc" )
601+ ):
602+ with open (".coveragerc" , "r" ) as f :
603+ coveragerc = f .read ()
604+ if "**/rest_asyncio.py" not in coveragerc :
605+ coveragerc = coveragerc .replace (
606+ "omit =\n " , "omit =\n **/rest_asyncio.py\n "
607+ )
608+ with open (".coveragerc" , "w" ) as f :
609+ f .write (coveragerc )
610+
549611 # Run the tests.
550612 session .run (
551613 "py.test" ,
@@ -564,15 +626,24 @@ def run_showcase_unit_tests(session, fail_under=100, rest_async_io_enabled=False
564626
565627
566628@nox .session (python = ALL_PYTHON )
629+ @nox .parametrize ("install_async_rest_extra" , [False , True ])
567630def showcase_unit (
568631 session ,
632+ install_async_rest_extra = False ,
569633 templates = "DEFAULT" ,
570634 other_opts : typing .Iterable [str ] = (),
571635):
572636 """Run the generated unit tests against the Showcase library."""
573- with showcase_library (session , templates = templates , other_opts = other_opts ) as lib :
637+ with showcase_library (
638+ session ,
639+ templates = templates ,
640+ other_opts = other_opts ,
641+ install_async_rest_extra = install_async_rest_extra ,
642+ ) as lib :
574643 session .chdir (lib )
575- run_showcase_unit_tests (session )
644+ run_showcase_unit_tests (
645+ session , install_async_rest_extra = install_async_rest_extra
646+ )
576647
577648
578649# TODO: `showcase_unit_w_rest_async` nox session runs showcase unit tests with the
0 commit comments