diff options
author | Gar <gar+gh@danger.computer> | 2021-07-28 01:38:07 +0300 |
---|---|---|
committer | nlf <quitlahok@gmail.com> | 2021-10-15 00:41:20 +0300 |
commit | 24273a862e54abfd022df9fc4b8c250bfe77817c (patch) | |
tree | d23b525c0d2dfc5d7235d679802f5f595910dbc6 | |
parent | 0f69d295bd5516f496af75ef29e7ae6304fa2ba5 (diff) |
feat(workspaces): add --include-workspace-root and explicit --no-workspacesfritzy/workspace-root
Adds a new config item that includes the workspace root. This also changes
--workspaces to a trinary, so that setting it to false will explicitly exclude
workspaces altogether.
PR-URL: https://github.com/npm/cli/pull/3890
Credit: @fritzy
Close: #3890
Reviewed-by: @wraithgar
72 files changed, 1221 insertions, 285 deletions
diff --git a/docs/content/commands/npm-audit.md b/docs/content/commands/npm-audit.md index 9fa8c0fcc..58c614d79 100644 --- a/docs/content/commands/npm-audit.md +++ b/docs/content/commands/npm-audit.md @@ -313,8 +313,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -327,17 +327,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-dedupe.md b/docs/content/commands/npm-dedupe.md index dcb2a98fe..377e17d81 100644 --- a/docs/content/commands/npm-dedupe.md +++ b/docs/content/commands/npm-dedupe.md @@ -247,8 +247,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -261,17 +261,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-diff.md b/docs/content/commands/npm-diff.md index cf0bbec15..8d05df779 100644 --- a/docs/content/commands/npm-diff.md +++ b/docs/content/commands/npm-diff.md @@ -286,8 +286,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -300,17 +300,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ## See Also diff --git a/docs/content/commands/npm-dist-tag.md b/docs/content/commands/npm-dist-tag.md index 4ad68ff56..a4e0243aa 100644 --- a/docs/content/commands/npm-dist-tag.md +++ b/docs/content/commands/npm-dist-tag.md @@ -106,8 +106,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -120,17 +120,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-docs.md b/docs/content/commands/npm-docs.md index 9f1387dae..970d17aa8 100644 --- a/docs/content/commands/npm-docs.md +++ b/docs/content/commands/npm-docs.md @@ -63,8 +63,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -77,17 +77,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-exec.md b/docs/content/commands/npm-exec.md index 82908d65e..db2353662 100644 --- a/docs/content/commands/npm-exec.md +++ b/docs/content/commands/npm-exec.md @@ -164,8 +164,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -178,17 +178,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### Examples diff --git a/docs/content/commands/npm-explain.md b/docs/content/commands/npm-explain.md index 4a8af2f70..5f05cac0f 100644 --- a/docs/content/commands/npm-explain.md +++ b/docs/content/commands/npm-explain.md @@ -85,8 +85,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a diff --git a/docs/content/commands/npm-find-dupes.md b/docs/content/commands/npm-find-dupes.md index e9dbac6d1..f7dc84f9c 100644 --- a/docs/content/commands/npm-find-dupes.md +++ b/docs/content/commands/npm-find-dupes.md @@ -174,8 +174,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -188,17 +188,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-fund.md b/docs/content/commands/npm-fund.md index 83c0b13d8..606b0a188 100644 --- a/docs/content/commands/npm-fund.md +++ b/docs/content/commands/npm-fund.md @@ -122,8 +122,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a diff --git a/docs/content/commands/npm-init.md b/docs/content/commands/npm-init.md index 7355c7588..a608061a9 100644 --- a/docs/content/commands/npm-init.md +++ b/docs/content/commands/npm-init.md @@ -200,8 +200,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -214,17 +214,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-install-test.md b/docs/content/commands/npm-install-test.md index c2f9ab3d2..c464e5bd0 100644 --- a/docs/content/commands/npm-install-test.md +++ b/docs/content/commands/npm-install-test.md @@ -241,8 +241,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -255,17 +255,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-install.md b/docs/content/commands/npm-install.md index de7378718..a103845d1 100644 --- a/docs/content/commands/npm-install.md +++ b/docs/content/commands/npm-install.md @@ -625,8 +625,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -639,17 +639,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### Algorithm diff --git a/docs/content/commands/npm-link.md b/docs/content/commands/npm-link.md index 5811a8b23..d4ef41ae9 100644 --- a/docs/content/commands/npm-link.md +++ b/docs/content/commands/npm-link.md @@ -325,8 +325,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -339,17 +339,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-ls.md b/docs/content/commands/npm-ls.md index 528140bee..3b33f0a36 100644 --- a/docs/content/commands/npm-ls.md +++ b/docs/content/commands/npm-ls.md @@ -227,8 +227,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -241,17 +241,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-outdated.md b/docs/content/commands/npm-outdated.md index 8eb5528c3..1b58a6afd 100644 --- a/docs/content/commands/npm-outdated.md +++ b/docs/content/commands/npm-outdated.md @@ -167,8 +167,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a diff --git a/docs/content/commands/npm-pack.md b/docs/content/commands/npm-pack.md index dda30512d..539459868 100644 --- a/docs/content/commands/npm-pack.md +++ b/docs/content/commands/npm-pack.md @@ -69,8 +69,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -83,17 +83,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### Description diff --git a/docs/content/commands/npm-pkg.md b/docs/content/commands/npm-pkg.md index bf6a2df5d..beee9c1c4 100644 --- a/docs/content/commands/npm-pkg.md +++ b/docs/content/commands/npm-pkg.md @@ -223,8 +223,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -237,12 +237,20 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> diff --git a/docs/content/commands/npm-prune.md b/docs/content/commands/npm-prune.md index 7bd7ad131..658ab2610 100644 --- a/docs/content/commands/npm-prune.md +++ b/docs/content/commands/npm-prune.md @@ -103,8 +103,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -117,17 +117,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-publish.md b/docs/content/commands/npm-publish.md index 946109de4..6958b1066 100644 --- a/docs/content/commands/npm-publish.md +++ b/docs/content/commands/npm-publish.md @@ -188,8 +188,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -202,17 +202,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-rebuild.md b/docs/content/commands/npm-rebuild.md index 19684796f..75e71c60e 100644 --- a/docs/content/commands/npm-rebuild.md +++ b/docs/content/commands/npm-rebuild.md @@ -89,8 +89,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -103,17 +103,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-repo.md b/docs/content/commands/npm-repo.md index c3c509e0b..cd47fde47 100644 --- a/docs/content/commands/npm-repo.md +++ b/docs/content/commands/npm-repo.md @@ -50,8 +50,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -64,17 +64,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-run-script.md b/docs/content/commands/npm-run-script.md index e436bc27f..6dd602d03 100644 --- a/docs/content/commands/npm-run-script.md +++ b/docs/content/commands/npm-run-script.md @@ -152,8 +152,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -166,17 +166,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + #### `if-present` * Default: false diff --git a/docs/content/commands/npm-set-script.md b/docs/content/commands/npm-set-script.md index e39b7a18c..869ceede0 100644 --- a/docs/content/commands/npm-set-script.md +++ b/docs/content/commands/npm-set-script.md @@ -44,8 +44,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -58,17 +58,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-uninstall.md b/docs/content/commands/npm-uninstall.md index c04e1a7fd..824d0d876 100644 --- a/docs/content/commands/npm-uninstall.md +++ b/docs/content/commands/npm-uninstall.md @@ -85,8 +85,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -99,17 +99,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-unpublish.md b/docs/content/commands/npm-unpublish.md index 1678bb305..13589a03e 100644 --- a/docs/content/commands/npm-unpublish.md +++ b/docs/content/commands/npm-unpublish.md @@ -107,8 +107,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -121,12 +121,20 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> diff --git a/docs/content/commands/npm-update.md b/docs/content/commands/npm-update.md index 57b9b91f9..ad02118e4 100644 --- a/docs/content/commands/npm-update.md +++ b/docs/content/commands/npm-update.md @@ -341,8 +341,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -355,17 +355,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### See Also diff --git a/docs/content/commands/npm-version.md b/docs/content/commands/npm-version.md index a02bf5bb9..91ab0dee0 100644 --- a/docs/content/commands/npm-version.md +++ b/docs/content/commands/npm-version.md @@ -103,8 +103,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -117,17 +117,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### Description diff --git a/docs/content/commands/npm-view.md b/docs/content/commands/npm-view.md index af354deb8..9a1793f13 100644 --- a/docs/content/commands/npm-view.md +++ b/docs/content/commands/npm-view.md @@ -127,8 +127,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -141,17 +141,39 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + <!-- AUTOGENERATED CONFIG DESCRIPTIONS END --> ### Output diff --git a/docs/content/using-npm/config.md b/docs/content/using-npm/config.md index fb155ebcf..ddabe01d7 100644 --- a/docs/content/using-npm/config.md +++ b/docs/content/using-npm/config.md @@ -806,6 +806,20 @@ This is experimental, and not implemented by the npm public registry. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### `include-workspace-root` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the `workspace` config, or +all workspaces via the `workspaces` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + #### `init-author-email` * Default: "" @@ -1769,8 +1783,8 @@ Valid values for the `workspace` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the `npm init` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -1783,12 +1797,20 @@ This value is not exported to the environment for child processes. #### `workspaces` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like `install` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the `node_modules` tree (install, update, etc.) +will link workspaces into the `node_modules` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the `workspace` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> diff --git a/lib/base-command.js b/lib/base-command.js index 870c69acc..c5bd3fd94 100644 --- a/lib/base-command.js +++ b/lib/base-command.js @@ -7,8 +7,6 @@ class BaseCommand { constructor (npm) { this.wrapWidth = 80 this.npm = npm - this.workspaces = null - this.workspacePaths = null } get name () { @@ -75,7 +73,13 @@ class BaseCommand { } async setWorkspaces (filters) { - const ws = await getWorkspaces(filters, { path: this.npm.localPrefix }) + if (this.isArboristCmd) + this.includeWorkspaceRoot = false + + const ws = await getWorkspaces(filters, { + path: this.npm.localPrefix, + includeWorkspaceRoot: this.includeWorkspaceRoot, + }) this.workspaces = ws this.workspaceNames = [...ws.keys()] this.workspacePaths = [...ws.values()] diff --git a/lib/diff.js b/lib/diff.js index 01658c466..b1a32705c 100644 --- a/lib/diff.js +++ b/lib/diff.js @@ -43,6 +43,7 @@ class Diff extends BaseCommand { 'tag', 'workspace', 'workspaces', + 'include-workspace-root', ] } diff --git a/lib/dist-tag.js b/lib/dist-tag.js index e32dcf61f..be44f39ff 100644 --- a/lib/dist-tag.js +++ b/lib/dist-tag.js @@ -14,7 +14,7 @@ class DistTag extends BaseCommand { /* istanbul ignore next - see test/lib/load-all-commands.js */ static get params () { - return ['workspace', 'workspaces'] + return ['workspace', 'workspaces', 'include-workspace-root'] } /* istanbul ignore next - see test/lib/load-all-commands.js */ diff --git a/lib/docs.js b/lib/docs.js index 69a19c35c..51f8be388 100644 --- a/lib/docs.js +++ b/lib/docs.js @@ -17,7 +17,13 @@ class Docs extends BaseCommand { /* istanbul ignore next - see test/lib/load-all-commands.js */ static get params () { - return ['browser', 'registry', 'workspace', 'workspaces'] + return [ + 'browser', + 'registry', + 'workspace', + 'workspaces', + 'include-workspace-root', + ] } /* istanbul ignore next - see test/lib/load-all-commands.js */ diff --git a/lib/exec.js b/lib/exec.js index 8c64c2f24..d11947483 100644 --- a/lib/exec.js +++ b/lib/exec.js @@ -35,7 +35,13 @@ class Exec extends BaseCommand { /* istanbul ignore next - see test/lib/load-all-commands.js */ static get params () { - return ['package', 'call', 'workspace', 'workspaces'] + return [ + 'package', + 'call', + 'workspace', + 'workspaces', + 'include-workspace-root', + ] } /* istanbul ignore next - see test/lib/load-all-commands.js */ diff --git a/lib/explain.js b/lib/explain.js index 7d785d7bf..fc7f57891 100644 --- a/lib/explain.js +++ b/lib/explain.js @@ -46,8 +46,15 @@ class Explain extends ArboristWorkspaceCmd { const arb = new Arborist({ path: this.npm.prefix, ...this.npm.flatOptions }) const tree = await arb.loadActual() - if (this.workspaceNames && this.workspaceNames.length) + if (this.npm.flatOptions.workspacesEnabled + && this.workspaceNames + && this.workspaceNames.length + ) this.filterSet = arb.workspaceDependencySet(tree, this.workspaceNames) + else if (!this.npm.flatOptions.workspacesEnabled) { + this.filterSet = + arb.excludeWorkspacesDependencySet(tree) + } const nodes = new Set() for (const arg of args) { diff --git a/lib/fund.js b/lib/fund.js index 1e0fa1ecb..97139f5bb 100644 --- a/lib/fund.js +++ b/lib/fund.js @@ -92,6 +92,7 @@ class Fund extends ArboristWorkspaceCmd { return } + // TODO: add !workspacesEnabled option handling to libnpmfund const fundingInfo = getFundingInfo(tree, { ...this.flatOptions, log: this.npm.log, diff --git a/lib/init.js b/lib/init.js index e4bd20b72..e654793ec 100644 --- a/lib/init.js +++ b/lib/init.js @@ -19,7 +19,7 @@ class Init extends BaseCommand { /* istanbul ignore next - see test/lib/load-all-commands.js */ static get params () { - return ['yes', 'force', 'workspace', 'workspaces'] + return ['yes', 'force', 'workspace', 'workspaces', 'include-workspace-root'] } /* istanbul ignore next - see test/lib/load-all-commands.js */ @@ -54,6 +54,10 @@ class Init extends BaseCommand { } async initWorkspaces (args, filters) { + // if the root package is uninitiated, take care of it first + if (this.npm.flatOptions.includeWorkspaceRoot) + await this.init(args) + // reads package.json for the top-level folder first, by doing this we // ensure the command throw if no package.json is found before trying // to create a workspace package.json file or its folders diff --git a/lib/link.js b/lib/link.js index febd90871..2437eb12e 100644 --- a/lib/link.js +++ b/lib/link.js @@ -185,6 +185,7 @@ class Link extends ArboristWorkspaceCmd { // atm but should be simple once we have a mocked registry again if (arg.name !== node.name /* istanbul ignore next */ || ( arg.version && + /* istanbul ignore next */ !semver.satisfies(node.version, arg.version) )) { foundNodes.push(node) @@ -82,6 +82,7 @@ class LS extends ArboristWorkspaceCmd { const production = this.npm.config.get('production') const unicode = this.npm.config.get('unicode') const packageLockOnly = this.npm.config.get('package-lock-only') + const workspacesEnabled = this.npm.flatOptions.workspacesEnabled const path = global ? resolve(this.npm.globalDir, '..') : this.npm.prefix @@ -100,12 +101,18 @@ class LS extends ArboristWorkspaceCmd { if (this.workspaceNames && this.workspaceNames.length) wsNodes = arb.workspaceNodes(tree, this.workspaceNames) const filterBySelectedWorkspaces = edge => { + if (!workspacesEnabled + && edge.from.isProjectRoot + && edge.to.isWorkspace + ) + return false + if (!wsNodes || !wsNodes.length) return true if (edge.from.isProjectRoot) { return edge.to && - edge.to.isWorkspace & + edge.to.isWorkspace && wsNodes.includes(edge.to.target) } diff --git a/lib/npm.js b/lib/npm.js index 1a7b06a34..63c5ede8a 100644 --- a/lib/npm.js +++ b/lib/npm.js @@ -137,7 +137,19 @@ const npm = module.exports = new class extends EventEmitter { const workspacesEnabled = this.config.get('workspaces') const workspacesFilters = this.config.get('workspace') + if (workspacesEnabled === false && workspacesFilters.length > 0) + return cb(new Error('Can not use --no-workspaces and --workspace at the same time')) + const filterByWorkspaces = workspacesEnabled || workspacesFilters.length > 0 + // normally this would go in the constructor, but our tests don't + // actually use a real npm object so this.npm.config isn't always + // populated. this is the compromise until we can make that a reality + // and then move this into the constructor. + impl.workspaces = this.config.get('workspaces') + impl.workspacePaths = null + // normally this would be evaluated in base-command#setWorkspaces, see + // above for explanation + impl.includeWorkspaceRoot = this.config.get('include-workspace-root') if (this.config.get('usage')) { this.output(impl.usage) diff --git a/lib/outdated.js b/lib/outdated.js index b3b630421..ab46b4536 100644 --- a/lib/outdated.js +++ b/lib/outdated.js @@ -62,7 +62,14 @@ class Outdated extends ArboristWorkspaceCmd { if (this.workspaceNames && this.workspaceNames.length) { this.filterSet = - arb.workspaceDependencySet(this.tree, this.workspaceNames) + arb.workspaceDependencySet( + this.tree, + this.workspaceNames, + this.npm.flatOptions.includeWorkspaceRoot + ) + } else if (!this.npm.flatOptions.workspacesEnabled) { + this.filterSet = + arb.excludeWorkspacesDependencySet(this.tree) } if (args.length !== 0) { diff --git a/lib/pack.js b/lib/pack.js index 8fc89db1a..848f8afd5 100644 --- a/lib/pack.js +++ b/lib/pack.js @@ -30,6 +30,7 @@ class Pack extends BaseCommand { 'pack-destination', 'workspace', 'workspaces', + 'include-workspace-root', ] } diff --git a/lib/publish.js b/lib/publish.js index 9c747eb50..32e70129f 100644 --- a/lib/publish.js +++ b/lib/publish.js @@ -36,7 +36,15 @@ class Publish extends BaseCommand { /* istanbul ignore next - see test/lib/load-all-commands.js */ static get params () { - return ['tag', 'access', 'dry-run', 'otp', 'workspace', 'workspaces'] + return [ + 'tag', + 'access', + 'dry-run', + 'otp', + 'workspace', + 'workspaces', + 'include-workspace-root', + ] } /* istanbul ignore next - see test/lib/load-all-commands.js */ diff --git a/lib/repo.js b/lib/repo.js index e0172d01f..bf1d1e7ff 100644 --- a/lib/repo.js +++ b/lib/repo.js @@ -19,7 +19,7 @@ class Repo extends BaseCommand { /* istanbul ignore next - see test/lib/load-all-commands.js */ static get params () { - return ['browser', 'workspace', 'workspaces'] + return ['browser', 'workspace', 'workspaces', 'include-workspace-root'] } /* istanbul ignore next - see test/lib/load-all-commands.js */ @@ -48,7 +48,13 @@ class Repo extends BaseCommand { } async get (pkg) { - const opts = { ...this.npm.flatOptions, fullMetadata: true } + // XXX It is very odd that `where` is how pacote knows to look anywhere + // other than the cwd. + const opts = { + ...this.npm.flatOptions, + where: this.npm.localPrefix, + fullMetadata: true, + } const mani = await pacote.manifest(pkg, opts) const r = mani.repository diff --git a/lib/run-script.js b/lib/run-script.js index 1daaeb990..de847ff28 100644 --- a/lib/run-script.js +++ b/lib/run-script.js @@ -38,6 +38,7 @@ class RunScript extends BaseCommand { return [ 'workspace', 'workspaces', + 'include-workspace-root', 'if-present', 'ignore-scripts', 'script-shell', diff --git a/lib/set-script.js b/lib/set-script.js index 24e4d8f20..185c4cc90 100644 --- a/lib/set-script.js +++ b/lib/set-script.js @@ -12,7 +12,7 @@ class SetScript extends BaseCommand { /* istanbul ignore next - see test/lib/load-all-commands.js */ static get params () { - return ['workspace', 'workspaces'] + return ['workspace', 'workspaces', 'include-workspace-root'] } /* istanbul ignore next - see test/lib/load-all-commands.js */ diff --git a/lib/utils/completion/installed-deep.js b/lib/utils/completion/installed-deep.js index 590955a1e..62686f9b2 100644 --- a/lib/utils/completion/installed-deep.js +++ b/lib/utils/completion/installed-deep.js @@ -7,6 +7,7 @@ const installedDeep = async (npm) => { depth, global, prefix, + workspacesEnabled, } = npm.flatOptions const getValues = (tree) => @@ -19,14 +20,18 @@ const installedDeep = async (npm) => { .sort((a, b) => (a.depth - b.depth) || localeCompare(a.name, b.name)) const res = new Set() - const gArb = new Arborist({ global: true, path: resolve(npm.globalDir, '..') }) + const gArb = new Arborist({ + global: true, + path: resolve(npm.globalDir, '..'), + workspacesEnabled, + }) const gTree = await gArb.loadActual({ global: true }) for (const node of getValues(gTree)) res.add(global ? node.name : [node.name, '-g']) if (!global) { - const arb = new Arborist({ global: false, path: prefix }) + const arb = new Arborist({ global: false, path: prefix, workspacesEnabled }) const tree = await arb.loadActual() for (const node of getValues(tree)) res.add(node.name) diff --git a/lib/utils/config/definitions.js b/lib/utils/config/definitions.js index 3bb8a4210..c9806b3c2 100644 --- a/lib/utils/config/definitions.js +++ b/lib/utils/config/definitions.js @@ -918,6 +918,19 @@ define('include-staged', { flatten, }) +define('include-workspace-root', { + default: false, + type: Boolean, + description: ` + Include the workspace root when workspaces are enabled for a command. + + When false, specifying individual workspaces via the \`workspace\` config, + or all workspaces via the \`workspaces\` flag, will cause npm to operate only + on the specified workspaces, and not on the root project. + `, + flatten, +}) + define('init-author-email', { default: '', type: String, @@ -2164,8 +2177,8 @@ define('workspace', { * Workspace names * Path to a workspace directory - * Path to a parent workspace directory (will result to selecting all of the - nested workspaces) + * Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the \`npm init\` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it @@ -2177,16 +2190,34 @@ define('workspace', { }) define('workspaces', { - default: false, - type: Boolean, + default: null, + type: [null, Boolean], short: 'ws', envExport: false, description: ` - Enable running a command in the context of **all** the configured + Set to true to run the command in the context of **all** configured workspaces. + + Explicitly setting this to false will cause commands like \`install\` to + ignore workspaces altogether. + When not set explicitly: + + - Commands that operate on the \`node_modules\` tree (install, update, + etc.) will link workspaces into the \`node_modules\` folder. + - Commands that do other things (test, exec, publish, etc.) will operate + on the root project, _unless_ one or more workspaces are specified in + the \`workspace\` config. `, flatten: (key, obj, flatOptions) => { definitions['user-agent'].flatten('user-agent', obj, flatOptions) + + // TODO: this is a derived value, and should be reworked when we have a + // pattern for derived value + + // workspacesEnabled is true whether workspaces is null or true + // commands contextually work with workspaces or not regardless of + // configuration, so we need an option specifically to disable workspaces + flatOptions.workspacesEnabled = obj[key] !== false }, }) diff --git a/lib/version.js b/lib/version.js index f3680fe8b..917a64747 100644 --- a/lib/version.js +++ b/lib/version.js @@ -26,6 +26,7 @@ class Version extends BaseCommand { 'sign-git-tag', 'workspace', 'workspaces', + 'include-workspace-root', ] } diff --git a/lib/view.js b/lib/view.js index 0124bfb7d..46b1b5edf 100644 --- a/lib/view.js +++ b/lib/view.js @@ -31,6 +31,7 @@ class View extends BaseCommand { 'json', 'workspace', 'workspaces', + 'include-workspace-root', ] } diff --git a/lib/workspaces/arborist-cmd.js b/lib/workspaces/arborist-cmd.js index cb6b66b8c..a75b351be 100644 --- a/lib/workspaces/arborist-cmd.js +++ b/lib/workspaces/arborist-cmd.js @@ -4,16 +4,21 @@ const BaseCommand = require('../base-command.js') class ArboristCmd extends BaseCommand { + get isArboristCmd () { + return true + } + /* istanbul ignore next - see test/lib/load-all-commands.js */ static get params () { return [ 'workspace', 'workspaces', + 'include-workspace-root', ] } execWorkspaces (args, filters, cb) { - this.setWorkspaces(filters) + this.setWorkspaces(filters, true) .then(() => { this.exec(args, cb) }) diff --git a/lib/workspaces/get-workspaces.js b/lib/workspaces/get-workspaces.js index 91b007455..3eb8e4865 100644 --- a/lib/workspaces/get-workspaces.js +++ b/lib/workspaces/get-workspaces.js @@ -5,11 +5,16 @@ const rpj = require('read-package-json-fast') // Returns an Map of paths to workspaces indexed by workspace name // { foo => '/path/to/foo' } -const getWorkspaces = async (filters, { path }) => { +const getWorkspaces = async (filters, { path, includeWorkspaceRoot }) => { // TODO we need a better error to be bubbled up here if this rpj call fails const pkg = await rpj(resolve(path, 'package.json')) const workspaces = await mapWorkspaces({ cwd: path, pkg }) - const res = filters.length ? new Map() : workspaces + let res = new Map() + if (includeWorkspaceRoot) + res.set(pkg.name, path) + + if (!filters.length) + res = new Map([...res, ...workspaces]) for (const filterArg of filters) { for (const [workspaceName, workspacePath] of workspaces.entries()) { diff --git a/tap-snapshots/test/lib/config.js.test.cjs b/tap-snapshots/test/lib/config.js.test.cjs index 0c57014de..ee121c28a 100644 --- a/tap-snapshots/test/lib/config.js.test.cjs +++ b/tap-snapshots/test/lib/config.js.test.cjs @@ -68,6 +68,7 @@ exports[`test/lib/config.js TAP config list --json > output matches snapshot 1`] "ignore-scripts": false, "include": [], "include-staged": false, + "include-workspace-root": false, "init-author-email": "", "init-author-name": "", "init-author-url": "", @@ -153,7 +154,7 @@ exports[`test/lib/config.js TAP config list --json > output matches snapshot 1`] "viewer": "{VIEWER}", "which": null, "workspace": [], - "workspaces": false, + "workspaces": null, "yes": null, "metrics-registry": "https://registry.npmjs.org/" } @@ -218,6 +219,7 @@ if-present = false ignore-scripts = false include = [] include-staged = false +include-workspace-root = false init-author-email = "" init-author-name = "" init-author-url = "" @@ -305,7 +307,7 @@ versions = false viewer = "{VIEWER}" which = null workspace = [] -workspaces = false +workspaces = null yes = null ; "global" config from {GLOBALPREFIX}/npmrc diff --git a/tap-snapshots/test/lib/dist-tag.js.test.cjs b/tap-snapshots/test/lib/dist-tag.js.test.cjs index 21d9331db..f651f7b67 100644 --- a/tap-snapshots/test/lib/dist-tag.js.test.cjs +++ b/tap-snapshots/test/lib/dist-tag.js.test.cjs @@ -18,7 +18,7 @@ npm dist-tag ls [<pkg>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: dist-tags @@ -40,7 +40,7 @@ npm dist-tag ls [<pkg>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: dist-tags @@ -71,7 +71,7 @@ npm dist-tag ls [<pkg>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: dist-tags @@ -93,7 +93,7 @@ npm dist-tag ls [<pkg>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: dist-tags @@ -121,7 +121,7 @@ npm dist-tag ls [<pkg>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: dist-tags @@ -179,7 +179,7 @@ npm dist-tag ls [<pkg>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: dist-tags diff --git a/tap-snapshots/test/lib/init.js.test.cjs b/tap-snapshots/test/lib/init.js.test.cjs index 95abbe6c1..3eb75be5f 100644 --- a/tap-snapshots/test/lib/init.js.test.cjs +++ b/tap-snapshots/test/lib/init.js.test.cjs @@ -5,6 +5,10 @@ * Make sure to inspect the output below. Do not ignore changes! */ 'use strict' +exports[`test/lib/init.js TAP npm init workspces with root > does not print helper info 1`] = ` +Array [] +` + exports[`test/lib/init.js TAP workspaces no args > should print helper info 1`] = ` Array [ Array [ diff --git a/tap-snapshots/test/lib/load-all-commands.js.test.cjs b/tap-snapshots/test/lib/load-all-commands.js.test.cjs index 9f811a005..6efecf208 100644 --- a/tap-snapshots/test/lib/load-all-commands.js.test.cjs +++ b/tap-snapshots/test/lib/load-all-commands.js.test.cjs @@ -56,7 +56,7 @@ Options: [--json] [--package-lock-only] [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help audit" for more info ` @@ -173,7 +173,7 @@ Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: ddp @@ -208,7 +208,7 @@ Options: [--diff-no-prefix] [--diff-src-prefix <path>] [--diff-dst-prefix <path>] [--diff-text] [-g|--global] [--tag <tag>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help diff" for more info ` @@ -225,7 +225,7 @@ npm dist-tag ls [<pkg>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: dist-tags @@ -243,7 +243,7 @@ npm docs [<pkgname> [<pkgname> ...]] Options: [--no-browser|--browser <browser>] [--registry <registry>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: home @@ -293,7 +293,7 @@ Options: [--package <pkg>[@<version>] [--package <pkg>[@<version>] ...]] [-c|--call <call>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: x @@ -343,7 +343,7 @@ Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help find-dupes" for more info ` @@ -421,7 +421,7 @@ npm init [<@scope>/]<name> (same as \`npx [<@scope>/]create-<name>\`) Options: [-y|--yes] [-f|--force] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] aliases: create, innit @@ -452,7 +452,7 @@ Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] aliases: i, in, ins, inst, insta, instal, isnt, isnta, isntal, add @@ -499,7 +499,7 @@ Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: it @@ -522,7 +522,7 @@ Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: ln @@ -542,7 +542,7 @@ Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--link] [--package-lock-only] [--unicode] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: la @@ -592,7 +592,7 @@ Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--link] [--package-lock-only] [--unicode] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: list @@ -661,7 +661,7 @@ npm pack [[<@scope>/]<pkg>...] Options: [--dry-run] [--json] [--pack-destination <pack-destination>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help pack" for more info ` @@ -740,7 +740,7 @@ npm prune [[<@scope>/]<pkg>...] Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--dry-run] [--json] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help prune" for more info ` @@ -756,7 +756,7 @@ npm publish [<folder>] Options: [--tag <tag>] [--access <restricted|public>] [--dry-run] [--otp <otp>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help publish" for more info ` @@ -772,7 +772,7 @@ npm rebuild [[<@scope>/]<name>[@<version>] ...] Options: [-g|--global] [--no-bin-links] [--ignore-scripts] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: rb @@ -790,7 +790,7 @@ npm repo [<pkgname> [<pkgname> ...]] Options: [--no-browser|--browser <browser>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help repo" for more info ` @@ -833,7 +833,7 @@ npm run-script <command> [-- <args>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] [--if-present] [--ignore-scripts] +[-ws|--workspaces] [--include-workspace-root] [--if-present] [--ignore-scripts] [--script-shell <script-shell>] aliases: run, rum, urn @@ -880,7 +880,7 @@ npm set-script [<script>] [<command>] Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help set-script" for more info ` @@ -1014,7 +1014,7 @@ npm uninstall [<@scope>/]<pkg>... Options: [-S|--save|--no-save|--save-prod|--save-dev|--save-optional|--save-peer] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] aliases: un, unlink, remove, rm, r @@ -1064,7 +1064,7 @@ Options: [--no-package-lock] [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] aliases: up, upgrade, udpate @@ -1083,7 +1083,7 @@ Options: [--allow-same-version] [--no-commit-hooks] [--no-git-tag-version] [--json] [--preid prerelease-id] [--sign-git-tag] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] alias: verison @@ -1100,7 +1100,7 @@ npm view [<@scope>/]<pkg>[@<version>] [<field>[.subfield]...] Options: [--json] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] aliases: v, info, show diff --git a/tap-snapshots/test/lib/ls.js.test.cjs b/tap-snapshots/test/lib/ls.js.test.cjs index c3d0a8764..c550f447c 100644 --- a/tap-snapshots/test/lib/ls.js.test.cjs +++ b/tap-snapshots/test/lib/ls.js.test.cjs @@ -547,6 +547,12 @@ exports[`test/lib/ls.js TAP ls loading a tree containing workspaces > should lis [0m[0m ` +exports[`test/lib/ls.js TAP ls loading a tree containing workspaces > should not list workspaces with --no-workspaces 1`] = ` +[0mworkspaces-tree@1.0.0 {CWD}/tap-testdir-ls-ls-loading-a-tree-containing-workspaces[0m +[0m\`-- (empty)[0m +[0m[0m +` + exports[`test/lib/ls.js TAP ls loading a tree containing workspaces > should print all tree and filter by dep within only the ws subtree 1`] = ` workspaces-tree@1.0.0 {CWD}/tap-testdir-ls-ls-loading-a-tree-containing-workspaces \`-- d@1.0.0 -> ./d diff --git a/tap-snapshots/test/lib/outdated.js.test.cjs b/tap-snapshots/test/lib/outdated.js.test.cjs index 9f589d013..15e815031 100644 --- a/tap-snapshots/test/lib/outdated.js.test.cjs +++ b/tap-snapshots/test/lib/outdated.js.test.cjs @@ -192,6 +192,10 @@ exports[`test/lib/outdated.js TAP workspaces > should display no results if ws h ` +exports[`test/lib/outdated.js TAP workspaces > should display only root outdated when ws disabled 1`] = ` + +` + exports[`test/lib/outdated.js TAP workspaces > should display parseable results filtered by ws 1`] = ` {CWD}/test/lib/tap-testdir-outdated-workspaces/node_modules/cat:cat@1.0.1:cat@1.0.0:cat@1.0.1:a diff --git a/tap-snapshots/test/lib/publish.js.test.cjs b/tap-snapshots/test/lib/publish.js.test.cjs index 7a7502e02..38457821a 100644 --- a/tap-snapshots/test/lib/publish.js.test.cjs +++ b/tap-snapshots/test/lib/publish.js.test.cjs @@ -51,7 +51,7 @@ npm publish [<folder>] Options: [--tag <tag>] [--access <restricted|public>] [--dry-run] [--otp <otp>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] -[-ws|--workspaces] +[-ws|--workspaces] [--include-workspace-root] Run "npm help publish" for more info { "code": "EUSAGE", diff --git a/tap-snapshots/test/lib/utils/config/definitions.js.test.cjs b/tap-snapshots/test/lib/utils/config/definitions.js.test.cjs index e0878c357..aaf59e6a2 100644 --- a/tap-snapshots/test/lib/utils/config/definitions.js.test.cjs +++ b/tap-snapshots/test/lib/utils/config/definitions.js.test.cjs @@ -63,6 +63,7 @@ Array [ "ignore-scripts", "include", "include-staged", + "include-workspace-root", "init-author-email", "init-author-name", "init-author-url", @@ -832,6 +833,19 @@ Allow installing "staged" published packages, as defined by [npm RFC PR This is experimental, and not implemented by the npm public registry. ` +exports[`test/lib/utils/config/definitions.js TAP > config description for include-workspace-root 1`] = ` +#### \`include-workspace-root\` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the \`workspace\` config, or +all workspaces via the \`workspaces\` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. +` + exports[`test/lib/utils/config/definitions.js TAP > config description for init-author-email 1`] = ` #### \`init-author-email\` @@ -1864,8 +1878,8 @@ Valid values for the \`workspace\` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the \`npm init\` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -1877,12 +1891,20 @@ This value is not exported to the environment for child processes. exports[`test/lib/utils/config/definitions.js TAP > config description for workspaces 1`] = ` #### \`workspaces\` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like \`install\` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the \`node_modules\` tree (install, update, etc.) +will link workspaces into the \`node_modules\` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the \`workspace\` config. + This value is not exported to the environment for child processes. ` diff --git a/tap-snapshots/test/lib/utils/config/describe-all.js.test.cjs b/tap-snapshots/test/lib/utils/config/describe-all.js.test.cjs index d092ba02b..dc55893d0 100644 --- a/tap-snapshots/test/lib/utils/config/describe-all.js.test.cjs +++ b/tap-snapshots/test/lib/utils/config/describe-all.js.test.cjs @@ -680,6 +680,20 @@ This is experimental, and not implemented by the npm public registry. <!-- automatically generated, do not edit manually --> <!-- see lib/utils/config/definitions.js --> +#### \`include-workspace-root\` + +* Default: false +* Type: Boolean + +Include the workspace root when workspaces are enabled for a command. + +When false, specifying individual workspaces via the \`workspace\` config, or +all workspaces via the \`workspaces\` flag, will cause npm to operate only on +the specified workspaces, and not on the root project. + +<!-- automatically generated, do not edit manually --> +<!-- see lib/utils/config/definitions.js --> + #### \`init-author-email\` * Default: "" @@ -1643,8 +1657,8 @@ Valid values for the \`workspace\` config are either: * Workspace names * Path to a workspace directory -* Path to a parent workspace directory (will result to selecting all of the - nested workspaces) +* Path to a parent workspace directory (will result in selecting all + workspaces within that folder) When set for the \`npm init\` command, this may be set to the folder of a workspace which does not yet exist, to create the folder and set it up as a @@ -1657,12 +1671,20 @@ This value is not exported to the environment for child processes. #### \`workspaces\` -* Default: false -* Type: Boolean +* Default: null +* Type: null or Boolean -Enable running a command in the context of **all** the configured +Set to true to run the command in the context of **all** configured workspaces. +Explicitly setting this to false will cause commands like \`install\` to +ignore workspaces altogether. When not set explicitly: + +- Commands that operate on the \`node_modules\` tree (install, update, etc.) +will link workspaces into the \`node_modules\` folder. - Commands that do +other things (test, exec, publish, etc.) will operate on the root project, +_unless_ one or more workspaces are specified in the \`workspace\` config. + This value is not exported to the environment for child processes. <!-- automatically generated, do not edit manually --> diff --git a/tap-snapshots/test/lib/utils/npm-usage.js.test.cjs b/tap-snapshots/test/lib/utils/npm-usage.js.test.cjs index 0fd36c7c1..0e48cfa61 100644 --- a/tap-snapshots/test/lib/utils/npm-usage.js.test.cjs +++ b/tap-snapshots/test/lib/utils/npm-usage.js.test.cjs @@ -211,7 +211,7 @@ All commands: [--json] [--package-lock-only] [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] Run "npm help audit" for more info @@ -314,7 +314,7 @@ All commands: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: ddp @@ -345,7 +345,7 @@ All commands: [--diff-no-prefix] [--diff-src-prefix <path>] [--diff-dst-prefix <path>] [--diff-text] [-g|--global] [--tag <tag>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] Run "npm help diff" for more info @@ -360,7 +360,7 @@ All commands: Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: dist-tags @@ -376,7 +376,7 @@ All commands: Options: [--no-browser|--browser <browser>] [--registry <registry>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: home @@ -420,7 +420,7 @@ All commands: [--package <pkg>[@<version>] [--package <pkg>[@<version>] ...]] [-c|--call <call>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: x @@ -464,7 +464,7 @@ All commands: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] Run "npm help find-dupes" for more info @@ -532,7 +532,7 @@ All commands: Options: [-y|--yes] [-f|--force] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] aliases: create, innit @@ -561,7 +561,7 @@ All commands: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] aliases: i, in, ins, inst, insta, instal, isnt, isnta, isntal, add @@ -604,7 +604,7 @@ All commands: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: it @@ -625,7 +625,7 @@ All commands: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: ln @@ -643,7 +643,7 @@ All commands: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--link] [--package-lock-only] [--unicode] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: la @@ -687,7 +687,7 @@ All commands: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--link] [--package-lock-only] [--unicode] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: list @@ -748,7 +748,7 @@ All commands: Options: [--dry-run] [--json] [--pack-destination <pack-destination>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] Run "npm help pack" for more info @@ -817,7 +817,7 @@ All commands: Options: [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--dry-run] [--json] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] Run "npm help prune" for more info @@ -831,7 +831,7 @@ All commands: Options: [--tag <tag>] [--access <restricted|public>] [--dry-run] [--otp <otp>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] Run "npm help publish" for more info @@ -845,7 +845,7 @@ All commands: Options: [-g|--global] [--no-bin-links] [--ignore-scripts] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: rb @@ -861,7 +861,7 @@ All commands: Options: [--no-browser|--browser <browser>] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] Run "npm help repo" for more info @@ -898,7 +898,7 @@ All commands: Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] [--if-present] [--ignore-scripts] + [-ws|--workspaces] [--include-workspace-root] [--if-present] [--ignore-scripts] [--script-shell <script-shell>] aliases: run, rum, urn @@ -939,7 +939,7 @@ All commands: Options: [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] Run "npm help set-script" for more info @@ -1055,7 +1055,7 @@ All commands: Options: [-S|--save|--no-save|--save-prod|--save-dev|--save-optional|--save-peer] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] aliases: un, unlink, remove, rm, r @@ -1099,7 +1099,7 @@ All commands: [--no-package-lock] [--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts] [--no-audit] [--no-bin-links] [--no-fund] [--dry-run] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] aliases: up, upgrade, udpate @@ -1116,7 +1116,7 @@ All commands: [--allow-same-version] [--no-commit-hooks] [--no-git-tag-version] [--json] [--preid prerelease-id] [--sign-git-tag] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] alias: verison @@ -1131,7 +1131,7 @@ All commands: Options: [--json] [-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]] - [-ws|--workspaces] + [-ws|--workspaces] [--include-workspace-root] aliases: v, info, show diff --git a/test/lib/explain.js b/test/lib/explain.js index f690aeb2c..ebec13619 100644 --- a/test/lib/explain.js +++ b/test/lib/explain.js @@ -2,7 +2,7 @@ const t = require('tap') const npm = { prefix: null, color: true, - flatOptions: {}, + flatOptions: { workspacesEnabled: true }, output: (...args) => { OUTPUT.push(args) }, @@ -301,3 +301,80 @@ t.test('workspaces', async t => { }) }) }) + +t.test('workspaces disabled', async t => { + npm.localPrefix = npm.prefix = t.testdir({ + 'package.json': JSON.stringify({ + name: 'workspaces-project', + version: '1.0.0', + workspaces: ['packages/*'], + dependencies: { + abbrev: '^1.0.0', + }, + }), + node_modules: { + a: t.fixture('symlink', '../packages/a'), + b: t.fixture('symlink', '../packages/b'), + c: t.fixture('symlink', '../packages/c'), + once: { + 'package.json': JSON.stringify({ + name: 'once', + version: '1.0.0', + dependencies: { + wrappy: '2.0.0', + }, + }), + }, + abbrev: { + 'package.json': JSON.stringify({ + name: 'abbrev', + version: '1.0.0', + }), + }, + wrappy: { + 'package.json': JSON.stringify({ + name: 'wrappy', + version: '2.0.0', + }), + }, + }, + packages: { + a: { + 'package.json': JSON.stringify({ + name: 'a', + version: '1.0.0', + dependencies: { + once: '1.0.0', + }, + }), + }, + b: { + 'package.json': JSON.stringify({ + name: 'b', + version: '1.0.0', + dependencies: { + abbrev: '^1.0.0', + }, + }), + }, + c: { + 'package.json': JSON.stringify({ + name: 'c', + version: '1.0.0', + }), + }, + }, + }) + + await new Promise((res, rej) => { + explain.npm.flatOptions.workspacesEnabled = false + explain.exec(['once'], err => { + t.equal( + err, + 'No dependencies found matching once', + 'should throw usage if dep not found when excluding ws' + ) + res() + }) + }) +}) diff --git a/test/lib/init.js b/test/lib/init.js index 1cefb1fc9..f11ce356f 100644 --- a/test/lib/init.js +++ b/test/lib/init.js @@ -513,3 +513,26 @@ t.test('workspaces', t => { t.end() }) +t.test('npm init workspces with root', t => { + t.teardown(() => { + npm._mockOutputs.length = 0 + }) + npm.localPrefix = t.testdir({}) + npm.flatOptions.includeWorkspaceRoot = true + + // init-package-json prints directly to console.log + // this avoids poluting test output with those logs + console.log = noop + + process.chdir(npm.localPrefix) + init.execWorkspaces([], ['packages/a'], err => { + if (err) + throw err + + const pkg = require(resolve(npm.localPrefix, 'package.json')) + t.equal(pkg.version, '1.0.0') + t.equal(pkg.license, 'ISC') + t.matchSnapshot(npm._mockOutputs, 'does not print helper info') + t.end() + }) +}) diff --git a/test/lib/ls.js b/test/lib/ls.js index 5f196501e..46dfd7fba 100644 --- a/test/lib/ls.js +++ b/test/lib/ls.js @@ -110,6 +110,7 @@ const config = { 'package-lock-only': false, } const flatOptions = { + workspacesEnabled: true, } const npm = mockNpm({ config, @@ -1530,6 +1531,25 @@ t.test('ls', (t) => { }) }) + await new Promise((res, rej) => { + config.all = false + config.depth = 0 + npm.color = true + npm.flatOptions.workspacesEnabled = false + ls.exec([], (err) => { + if (err) + rej(err) + + t.matchSnapshot(redactCwd(result), + 'should not list workspaces with --no-workspaces') + config.all = true + config.depth = Infinity + npm.color = false + npm.flatOptions.workspacesEnabled = true + res() + }) + }) + // --all await new Promise((res, rej) => { ls.exec([], (err) => { diff --git a/test/lib/npm.js b/test/lib/npm.js index 7d6176247..1451cd879 100644 --- a/test/lib/npm.js +++ b/test/lib/npm.js @@ -292,6 +292,44 @@ t.test('npm.load', t => { await new Promise((res) => setTimeout(res)) }) + t.test('--no-workspaces with --workspace', async t => { + const dir = t.testdir({ + packages: { + a: { + 'package.json': JSON.stringify({ + name: 'a', + version: '1.0.0', + scripts: { test: 'echo test a' }, + }), + }, + }, + 'package.json': JSON.stringify({ + name: 'root', + version: '1.0.0', + workspaces: ['./packages/*'], + }), + }) + process.argv = [ + process.execPath, + process.argv[1], + '--userconfig', resolve(dir, '.npmrc'), + '--color', 'false', + '--workspaces', 'false', + '--workspace', 'a', + ] + const { npm } = mockNpm(t) + await npm.load() + npm.localPrefix = dir + await new Promise((res, rej) => { + npm.commands.run([], er => { + if (!er) + return rej(new Error('Expected an error')) + t.match(er.message, 'Can not use --no-workspaces and --workspace at the same time') + res() + }) + }) + }) + t.test('workspace-aware configs and commands', async t => { const dir = t.testdir({ packages: { diff --git a/test/lib/outdated.js b/test/lib/outdated.js index 518436d0a..acd5c25e8 100644 --- a/test/lib/outdated.js +++ b/test/lib/outdated.js @@ -83,6 +83,10 @@ const globalDir = t.testdir({ }, }) +const flatOptions = { + workspacesEnabled: true, +} + const outdated = (dir, opts) => { logs = '' const Outdated = t.mock('../../lib/outdated.js', { @@ -94,6 +98,7 @@ const outdated = (dir, opts) => { ...opts, localPrefix: dir, prefix: dir, + flatOptions, globalDir: `${globalDir}/node_modules`, output, }) @@ -562,6 +567,21 @@ t.test('workspaces', async t => { }) await new Promise((res, rej) => { + flatOptions.workspacesEnabled = false + outdated(testDir, {}).exec([], err => { + if (err) + rej(err) + + // TODO: This should display dog, but doesn't because arborist filters + // workspace deps even if they're also root deps + // This will be fixed in a future arborist version + t.matchSnapshot(logs, 'should display only root outdated when ws disabled') + flatOptions.workspacesEnabled = true + res() + }) + }) + + await new Promise((res, rej) => { outdated(testDir, { config: { json: true, diff --git a/test/lib/publish.js b/test/lib/publish.js index df73b6863..6b0021db6 100644 --- a/test/lib/publish.js +++ b/test/lib/publish.js @@ -57,6 +57,7 @@ t.test('should publish with libnpmpublish, passing through flatOptions and respe const npm = mockNpm({ flatOptions: { customValue: true, + workspacesEnabled: true, }, }) npm.config.getCredentialsByURI = (uri) => { diff --git a/test/lib/repo.js b/test/lib/repo.js index e1ac90b1e..41bff2744 100644 --- a/test/lib/repo.js +++ b/test/lib/repo.js @@ -1,5 +1,5 @@ const t = require('tap') -const { fake: mockNpm } = require('../fixtures/mock-npm.js') +const { real: mockNpm } = require('../fixtures/mock-npm.js') const { join, sep } = require('path') const pkgDirs = t.testdir({ @@ -154,6 +154,7 @@ const pkgDirs = t.testdir({ name: 'workspaces-test', version: '1.2.3-test', workspaces: ['workspace-a', 'workspace-b', 'workspace-c'], + repository: 'https://github.com/npm/workspaces-test', }), 'workspace-a': { 'package.json': JSON.stringify({ @@ -185,19 +186,17 @@ const openUrl = async (npm, url, errMsg) => { opened[url]++ } -const Repo = t.mock('../../lib/repo.js', { +const { command, npm } = mockNpm(t, { '../../lib/utils/open-url.js': openUrl, }) -const flatOptions = {} -const npm = mockNpm({ flatOptions }) -const repo = new Repo(npm) +t.before(async () => { + await npm.load() +}) t.afterEach(() => opened = {}) t.test('open repo urls', t => { - // XXX It is very odd that `where` is how pacote knows to look anywhere other - // than the cwd. I would think npm.localPrefix would factor in somehow - flatOptions.where = pkgDirs + npm.localPrefix = pkgDirs const expect = { hostedgit: 'https://github.com/foo/hostedgit', hostedgitat: 'https://github.com/foo/hostedgitat', @@ -227,22 +226,19 @@ t.test('open repo urls', t => { const keys = Object.keys(expect) t.plan(keys.length) keys.forEach(pkg => { - t.test(pkg, t => { - repo.exec([['.', pkg].join(sep)], (err) => { - if (err) - throw err - const url = expect[pkg] - t.match({ - [url]: 1, - }, opened, `opened ${url}`, {opened}) - t.end() - }) + t.test(pkg, async t => { + await command('repo', [['.', pkg].join(sep)]) + const url = expect[pkg] + t.match({ + [url]: 1, + }, opened, `opened ${url}`, {opened}) + t.end() }) }) }) t.test('fail if cannot figure out repo url', t => { - flatOptions.where = pkgDirs + npm.localPrefix = pkgDirs const cases = [ 'norepo', 'repoobbj-nourl', @@ -253,57 +249,65 @@ t.test('fail if cannot figure out repo url', t => { t.plan(cases.length) cases.forEach(pkg => { - t.test(pkg, t => { - repo.exec([['.', pkg].join(sep)], (err) => { - t.match(err, { pkgid: pkg }) - t.end() - }) + t.test(pkg, async t => { + t.rejects( + command('repo', [['.', pkg].join(sep)]), + { pkgid: pkg } + ) }) }) }) -t.test('open default package if none specified', t => { - flatOptions.where = pkgDirs - repo.exec([], (er) => { - if (er) - throw er - t.equal(opened['https://example.com/thispkg'], 1, 'opened expected url', {opened}) - t.end() - }) +t.test('open default package if none specified', async t => { + npm.localPrefix = pkgDirs + await command('repo', []) + t.equal(opened['https://example.com/thispkg'], 1, 'opened expected url', {opened}) }) t.test('workspaces', t => { - flatOptions.where = undefined npm.localPrefix = join(pkgDirs, 'workspaces') - t.test('all workspaces', (t) => { - repo.execWorkspaces([], [], (err) => { - t.notOk(err) - t.match({ - 'https://repo.workspace-a/': 1, // Gets translated to https! - 'https://github.com/npm/workspace-b': 1, - }, opened, 'opened two valid repo urls') - t.end() - }) + t.afterEach(() => { + npm.config.set('workspaces', null) + npm.config.set('workspace', []) + npm.config.set('include-workspace-root', false) }) - t.test('one workspace', (t) => { - repo.execWorkspaces([], ['workspace-a'], (err) => { - t.notOk(err) - t.match({ - 'https://repo.workspace-a/': 1, - }, opened, 'opened one requested repo urls') - t.end() - }) + t.test('include workspace root', async (t) => { + npm.config.set('workspaces', true) + npm.config.set('include-workspace-root', true) + await command('repo', []) + t.match({ + 'https://github.com/npm/workspaces-test': 1, + 'https://repo.workspace-a/': 1, // Gets translated to https! + 'https://github.com/npm/workspace-b': 1, + }, opened, 'opened two valid repo urls') }) - t.test('invalid workspace', (t) => { - repo.execWorkspaces([], ['workspace-x'], (err) => { - t.match(err, /No workspaces found/) - t.match(err, /workspace-x/) - t.match({}, opened, 'opened no repo urls') - t.end() - }) + t.test('all workspaces', async (t) => { + npm.config.set('workspaces', true) + await command('repo', []) + t.match({ + 'https://repo.workspace-a/': 1, // Gets translated to https! + 'https://github.com/npm/workspace-b': 1, + }, opened, 'opened two valid repo urls') + }) + + t.test('one workspace', async (t) => { + npm.config.set('workspace', ['workspace-a']) + await command('repo', []) + t.match({ + 'https://repo.workspace-a/': 1, + }, opened, 'opened one requested repo urls') + }) + + t.test('invalid workspace', async (t) => { + npm.config.set('workspace', ['workspace-x']) + await t.rejects( + command('repo', []), + /workspace-x/ + ) + t.match({}, opened, 'opened no repo urls') }) t.end() }) diff --git a/test/lib/utils/completion/installed-deep.js b/test/lib/utils/completion/installed-deep.js index aa0d85ec1..f0e36faee 100644 --- a/test/lib/utils/completion/installed-deep.js +++ b/test/lib/utils/completion/installed-deep.js @@ -6,6 +6,7 @@ let globalDir = 'MISSING_GLOBAL_DIR' const _flatOptions = { depth: Infinity, global: false, + workspacesEnabled: true, get prefix () { return prefix }, diff --git a/test/lib/utils/config/definitions.js b/test/lib/utils/config/definitions.js index 88993303b..622e603bc 100644 --- a/test/lib/utils/config/definitions.js +++ b/test/lib/utils/config/definitions.js @@ -875,3 +875,20 @@ t.test('workspace', t => { t.match(flat.userAgent, /workspaces\/true/) t.end() }) + +t.test('workspaces derived', t => { + const obj = { + workspaces: ['a'], + 'user-agent': definitions['user-agent'].default, + } + const flat = {} + definitions.workspaces.flatten('workspaces', obj, flat) + t.equal(flat.workspacesEnabled, true) + obj.workspaces = null + definitions.workspaces.flatten('workspaces', obj, flat) + t.equal(flat.workspacesEnabled, true) + obj.workspaces = false + definitions.workspaces.flatten('workspaces', obj, flat) + t.equal(flat.workspacesEnabled, false) + t.end() +}) diff --git a/test/lib/workspaces/get-workspaces.js b/test/lib/workspaces/get-workspaces.js index 4ea055e02..0f51d95fc 100644 --- a/test/lib/workspaces/get-workspaces.js +++ b/test/lib/workspaces/get-workspaces.js @@ -86,6 +86,17 @@ t.test('get-workspaces', async t => { 'should filter by package name' ) + workspaces = await getWorkspaces(['a', 'b'], { path, includeWorkspaceRoot: true }) + t.same( + clean(workspaces, path), + new Map(Object.entries({ + x: '{PATH}', + a: '{PATH}/packages/a', + b: '{PATH}/packages/b', + })), + 'include rootspace root' + ) + workspaces = await getWorkspaces(['./packages/c'], { path }) t.same( clean(workspaces, path), |