From e3190cf911cbc99add9b3679c8ea3badd7dbef25 Mon Sep 17 00:00:00 2001 From: Philipp Schneeberger <43273616+schneebuzz@users.noreply.github.com> Date: Wed, 9 Oct 2024 11:18:11 +0200 Subject: [PATCH 1/4] feat(install): add --all-groups flag to include all dependency groups for installation --- docs/cli.md | 8 +++++ src/poetry/console/commands/group_command.py | 12 +++++++ src/poetry/console/commands/install.py | 16 ++++++++-- tests/console/commands/test_install.py | 33 ++++++++++++++++++-- 4 files changed, 64 insertions(+), 5 deletions(-) diff --git a/docs/cli.md b/docs/cli.md index 67020f2c33c..fc8bbe1f41c 100644 --- a/docs/cli.md +++ b/docs/cli.md @@ -168,6 +168,12 @@ You can also select optional dependency groups with the `--with` option. poetry install --with test,docs ``` +To install all dependency groups including the optional groups, use the ``--all-groups`` flag. + +```bash +poetry install --all-groups +``` + It's also possible to only install specific dependency groups by using the `only` option. ```bash @@ -261,12 +267,14 @@ poetry install --compile * `--dry-run`: Output the operations but do not execute anything (implicitly enables --verbose). * `--extras (-E)`: Features to install (multiple values allowed). * `--all-extras`: Install all extra features (conflicts with --extras). +* `--all-groups`: Install dependencies from all groups (conflicts with --only). * `--compile`: Compile Python source files to bytecode. * `--no-dev`: Do not install dev dependencies. (**Deprecated**, use `--only main` or `--without dev` instead) * `--remove-untracked`: Remove dependencies not presented in the lock file. (**Deprecated**, use `--sync` instead) {{% note %}} When `--only` is specified, `--with` and `--without` options are ignored. +When `--all-groups` is specified, the `--with` option is ignored. {{% /note %}} diff --git a/src/poetry/console/commands/group_command.py b/src/poetry/console/commands/group_command.py index 750666f69ae..edbc92b2ca9 100644 --- a/src/poetry/console/commands/group_command.py +++ b/src/poetry/console/commands/group_command.py @@ -80,6 +80,18 @@ def activated_groups(self) -> set[str]: for groups in self.option(key, "") for group in groups.split(",") } + + if self.option("all-groups"): + if self.option("with"): + self.line_error( + "The `--with` option is" + " ignored when using the `--all-groups`" + " option." + ) + groups["with"] = self.poetry.package.dependency_group_names( + include_optional=True + ) + self._validate_group_options(groups) for opt, new, group in [ diff --git a/src/poetry/console/commands/install.py b/src/poetry/console/commands/install.py index d40e6f079b7..2cb561e790d 100644 --- a/src/poetry/console/commands/install.py +++ b/src/poetry/console/commands/install.py @@ -62,6 +62,7 @@ class InstallCommand(InstallerCommand): multiple=True, ), option("all-extras", None, "Install all extra dependencies."), + option("all-groups", None, "Install dependencies from all groups."), option("only-root", None, "Exclude all dependencies."), option( "compile", @@ -116,12 +117,14 @@ def handle(self) -> int: return 1 if self.option("only-root") and any( - self.option(key) for key in {"with", "without", "only"} + self.option(key) for key in {"with", "without", "only", "all-groups"} ): self.line_error( "The `--with`," - " `--without` and" - " `--only` options cannot be used with" + " `--without`," + " `--only` and" + " `--all-groups`" + " options cannot be used with" " the `--only-root`" " option." ) @@ -134,6 +137,13 @@ def handle(self) -> int: ) return 1 + if self.option("only") and self.option("all-groups"): + self.line_error( + "You cannot specify `--all-groups`" + " when using `--only`." + ) + return 1 + extras: list[str] if self.option("all-extras"): extras = list(self.poetry.package.extras.keys()) diff --git a/tests/console/commands/test_install.py b/tests/console/commands/test_install.py index df7557749f8..9b0e6aef77b 100644 --- a/tests/console/commands/test_install.py +++ b/tests/console/commands/test_install.py @@ -57,6 +57,12 @@ [tool.poetry.group.bam.dependencies] bam = "^1.4" +[tool.poetry.group.bum] +optional = true + +[tool.poetry.group.bum.dependencies] +bam = "^1.5" + [tool.poetry.extras] extras_a = [ "fizz" ] extras_b = [ "buzz" ] @@ -104,6 +110,12 @@ def _project_factory( ("--without foo,bar", {MAIN_GROUP, "baz", "bim"}), (f"--without {MAIN_GROUP}", {"foo", "bar", "baz", "bim"}), ("--with foo,bar --without baz --without bim --only bam", {"bam"}), + ("--all-groups", {MAIN_GROUP, "foo", "bar", "baz", "bim", "bam", "bum"}), + ( + "--all-groups --with bum", + {MAIN_GROUP, "foo", "bar", "baz", "bim", "bam", "bum"}, + ), + ("--all-groups --without bum", {MAIN_GROUP, "foo", "bar", "baz", "bim", "bam"}), # net result zero options ("--with foo", {MAIN_GROUP, "foo", "bar", "baz", "bim"}), ("--without bam", {MAIN_GROUP, "foo", "bar", "baz", "bim"}), @@ -287,9 +299,10 @@ def test_extras_conflicts_all_extras( "--without foo", "--with foo,bar --without baz", "--only foo", + "--all-groups", ], ) -def test_only_root_conflicts_with_without_only( +def test_only_root_conflicts_with_without_only_all_groups( options: str, tester: CommandTester, mocker: MockerFixture, @@ -302,11 +315,27 @@ def test_only_root_conflicts_with_without_only( assert tester.status_code == 1 assert ( tester.io.fetch_error() - == "The `--with`, `--without` and `--only` options cannot be used with" + == "The `--with`, `--without`, `--only` and `--all-groups` options cannot be used with" " the `--only-root` option.\n" ) +def test_only_conflicts_with_all_groups( + tester: CommandTester, + mocker: MockerFixture, +) -> None: + assert isinstance(tester.command, InstallerCommand) + mocker.patch.object(tester.command.installer, "run", return_value=0) + + tester.execute("--only foo --all-groups") + + assert tester.status_code == 1 + assert ( + tester.io.fetch_error() + == "You cannot specify `--all-groups` when using `--only`.\n" + ) + + @pytest.mark.parametrize( ("options", "valid_groups", "should_raise"), [ From b5e7c98615c75e2a0ff64b6329e27a91160b291b Mon Sep 17 00:00:00 2001 From: Philipp Schneeberger <43273616+schneebuzz@users.noreply.github.com> Date: Sun, 13 Oct 2024 14:07:05 +0200 Subject: [PATCH 2/4] refactor: make `--all-groups` conflict with `--only`, `--without` and `--with` --- src/poetry/console/commands/group_command.py | 6 ---- src/poetry/console/commands/install.py | 10 +++++-- tests/console/commands/test_install.py | 29 ++++++++++---------- 3 files changed, 21 insertions(+), 24 deletions(-) diff --git a/src/poetry/console/commands/group_command.py b/src/poetry/console/commands/group_command.py index edbc92b2ca9..822d6131a20 100644 --- a/src/poetry/console/commands/group_command.py +++ b/src/poetry/console/commands/group_command.py @@ -82,12 +82,6 @@ def activated_groups(self) -> set[str]: } if self.option("all-groups"): - if self.option("with"): - self.line_error( - "The `--with` option is" - " ignored when using the `--all-groups`" - " option." - ) groups["with"] = self.poetry.package.dependency_group_names( include_optional=True ) diff --git a/src/poetry/console/commands/install.py b/src/poetry/console/commands/install.py index 2cb561e790d..e5f9a7fc070 100644 --- a/src/poetry/console/commands/install.py +++ b/src/poetry/console/commands/install.py @@ -137,10 +137,14 @@ def handle(self) -> int: ) return 1 - if self.option("only") and self.option("all-groups"): + if ( + self.option("only") or self.option("with") or self.option("without") + ) and self.option("all-groups"): self.line_error( - "You cannot specify `--all-groups`" - " when using `--only`." + "You cannot specify `--with`," + " `--without`, or" + " `--only` when using" + " `--all-groups`." ) return 1 diff --git a/tests/console/commands/test_install.py b/tests/console/commands/test_install.py index 9b0e6aef77b..30cf4f7d55a 100644 --- a/tests/console/commands/test_install.py +++ b/tests/console/commands/test_install.py @@ -57,12 +57,6 @@ [tool.poetry.group.bam.dependencies] bam = "^1.4" -[tool.poetry.group.bum] -optional = true - -[tool.poetry.group.bum.dependencies] -bam = "^1.5" - [tool.poetry.extras] extras_a = [ "fizz" ] extras_b = [ "buzz" ] @@ -110,12 +104,7 @@ def _project_factory( ("--without foo,bar", {MAIN_GROUP, "baz", "bim"}), (f"--without {MAIN_GROUP}", {"foo", "bar", "baz", "bim"}), ("--with foo,bar --without baz --without bim --only bam", {"bam"}), - ("--all-groups", {MAIN_GROUP, "foo", "bar", "baz", "bim", "bam", "bum"}), - ( - "--all-groups --with bum", - {MAIN_GROUP, "foo", "bar", "baz", "bim", "bam", "bum"}, - ), - ("--all-groups --without bum", {MAIN_GROUP, "foo", "bar", "baz", "bim", "bam"}), + ("--all-groups", {MAIN_GROUP, "foo", "bar", "baz", "bim", "bam"}), # net result zero options ("--with foo", {MAIN_GROUP, "foo", "bar", "baz", "bim"}), ("--without bam", {MAIN_GROUP, "foo", "bar", "baz", "bim"}), @@ -320,19 +309,29 @@ def test_only_root_conflicts_with_without_only_all_groups( ) -def test_only_conflicts_with_all_groups( +@pytest.mark.parametrize( + "options", + [ + "--with foo", + "--without foo", + "--with foo,bar --without baz", + "--only foo", + ], +) +def test_all_groups_conflicts_with_only_with_without( + options: str, tester: CommandTester, mocker: MockerFixture, ) -> None: assert isinstance(tester.command, InstallerCommand) mocker.patch.object(tester.command.installer, "run", return_value=0) - tester.execute("--only foo --all-groups") + tester.execute(f"{options} --all-groups") assert tester.status_code == 1 assert ( tester.io.fetch_error() - == "You cannot specify `--all-groups` when using `--only`.\n" + == "You cannot specify `--with`, `--without`, or `--only` when using `--all-groups`.\n" ) From 1c410aa7ac5778a879ce3fb239f04c344d39d9e5 Mon Sep 17 00:00:00 2001 From: Philipp Schneeberger <43273616+schneebuzz@users.noreply.github.com> Date: Sun, 13 Oct 2024 14:00:31 +0200 Subject: [PATCH 3/4] docs(cli): update docs for `--all-groups`, consistent options formatting --- docs/cli.md | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/docs/cli.md b/docs/cli.md index fc8bbe1f41c..b76722a6ef6 100644 --- a/docs/cli.md +++ b/docs/cli.md @@ -264,10 +264,10 @@ poetry install --compile * `--sync`: Synchronize the environment with the locked packages and the specified groups. * `--no-root`: Do not install the root package (your project). * `--no-directory`: Skip all directory path dependencies (including transitive ones). -* `--dry-run`: Output the operations but do not execute anything (implicitly enables --verbose). +* `--dry-run`: Output the operations but do not execute anything (implicitly enables `--verbose`). * `--extras (-E)`: Features to install (multiple values allowed). -* `--all-extras`: Install all extra features (conflicts with --extras). -* `--all-groups`: Install dependencies from all groups (conflicts with --only). +* `--all-extras`: Install all extra features (conflicts with `--extras`). +* `--all-groups`: Install dependencies from all groups (conflicts with `--only`, `--with`, and `--without`). * `--compile`: Compile Python source files to bytecode. * `--no-dev`: Do not install dev dependencies. (**Deprecated**, use `--only main` or `--without dev` instead) * `--remove-untracked`: Remove dependencies not presented in the lock file. (**Deprecated**, use `--sync` instead) @@ -308,7 +308,7 @@ You can do this using the `add` command. * `--without`: The dependency groups to ignore. * `--with`: The optional dependency groups to include. * `--only`: The only dependency groups to include. -* `--dry-run` : Outputs the operations but will not execute anything (implicitly enables --verbose). +* `--dry-run` : Outputs the operations but will not execute anything (implicitly enables `--verbose`). * `--no-dev` : Do not update the development dependencies. (**Deprecated**, use `--only main` or `--without dev` instead) * `--lock` : Do not perform install (only update the lockfile). * `--sync`: Synchronize the environment with the locked packages and the specified groups. @@ -470,7 +470,7 @@ about dependency groups. * `--platform`: Platforms for which the dependency must be installed. * `--source`: Name of the source to use to install the package. * `--allow-prereleases`: Accept prereleases. -* `--dry-run`: Output the operations but do not execute anything (implicitly enables --verbose). +* `--dry-run`: Output the operations but do not execute anything (implicitly enables `--verbose`). * `--lock`: Do not perform install (only update the lockfile). @@ -496,7 +496,7 @@ about dependency groups. * `--group (-G)`: The group to remove the dependency from. * `--dev (-D)`: Removes a package from the development dependencies. (**Deprecated**, use `-G dev` instead) -* `--dry-run` : Outputs the operations but will not execute anything (implicitly enables --verbose). +* `--dry-run` : Outputs the operations but will not execute anything (implicitly enables `--verbose`). * `--lock`: Do not perform operations (only update the lockfile). @@ -1007,7 +1007,7 @@ poetry self add artifacts-keyring * `--extras (-E)`: Extras to activate for the dependency. (multiple values allowed) * `--allow-prereleases`: Accept prereleases. * `--source`: Name of the source to use to install the package. -* `--dry-run`: Output the operations but do not execute anything (implicitly enables --verbose). +* `--dry-run`: Output the operations but do not execute anything (implicitly enables `--verbose`). ### self update @@ -1025,7 +1025,7 @@ poetry self update #### Options * `--preview`: Allow the installation of pre-release versions. -* `--dry-run`: Output the operations but do not execute anything (implicitly enables --verbose). +* `--dry-run`: Output the operations but do not execute anything (implicitly enables `--verbose`). ### self lock @@ -1079,7 +1079,7 @@ poetry self remove poetry-plugin-export #### Options -* `--dry-run`: Outputs the operations but will not execute anything (implicitly enables --verbose). +* `--dry-run`: Outputs the operations but will not execute anything (implicitly enables `--verbose`). ### self install @@ -1098,4 +1098,4 @@ poetry self install --sync #### Options * `--sync`: Synchronize the environment with the locked packages and the specified groups. -* `--dry-run`: Output the operations but do not execute anything (implicitly enables --verbose). +* `--dry-run`: Output the operations but do not execute anything (implicitly enables `--verbose`). From 0b0c838a841a293e951f2a599c0450fc513ad933 Mon Sep 17 00:00:00 2001 From: Philipp Schneeberger <43273616+schneebuzz@users.noreply.github.com> Date: Tue, 15 Oct 2024 08:06:57 +0200 Subject: [PATCH 4/4] docs(cli): remove leftover note about `--all-groups` --- docs/cli.md | 1 - 1 file changed, 1 deletion(-) diff --git a/docs/cli.md b/docs/cli.md index d1fd23303cc..fb94f416ce1 100644 --- a/docs/cli.md +++ b/docs/cli.md @@ -269,7 +269,6 @@ poetry install --compile {{% note %}} When `--only` is specified, `--with` and `--without` options are ignored. -When `--all-groups` is specified, the `--with` option is ignored. {{% /note %}}