How to associate registry with scope in Yarn 2 without breaking auth?

Viewed 3127

This article suggests adding configuration to .npmrc in your project to associate a scope with a private registry to reduce the risk of a npm substitution attack (where someone might deliberately publish a malicious public package with the same name).

How can we achieve a similar effect in a Yarn 2 project? I've tried adding a .yarnrc.yml file in my project root:

npmScopes:
  someScope:
    npmRegistryServer: https://npm.pkg.github.com

We also have a home-directory ~/.yarnrc.yml for each developer with similar configuration, but additionally with an appropriate npmAuthToken to authenticate.

However, when I do a yarn install, I get an Invalid authentication (as an anonymous user) error for packages in that scope. Presumably the project-specific .yarnrc.yml is overriding the settings from the per-user ~/.yarnrc.yml, so the auth information is no longer present?

The mitigation I'm after is that if a developer forgets to run yarn npm login, then it won't check the public registry for packages in a particular scope. Is there a way to do this in Yarn 2?

2 Answers

I just had the same problem. The problem is that you have to define the authentication per section (like pointed out in this issue comment). This also applies to npmRegistries.

npmScopes:
  someScope:
    npmRegistryServer: <your-registry-server>
    npmAuthToken: <your-token>
    npmAlwaysAuth: true

Mind that duplicated configurations in hierarchical definitions of .yarnrc.yml won't be merged but replaced (see this comment). Thus, if npmScopes is already declared in the home directory it is overwritten by the declaration in the project.

As @R.Hagl mentioned, the configurations are not merged but replaced. This is meant to be fixed in the next major release of yarn (4?).

At the moment to get it working, you have to put the full configuration into the global ~/yarnrc.yml:

npmScopes:
  someScope:
    npmRegistryServer: https://npm.pkg.github.com
    npmAuthToken: <your-token>
    npmAlwaysAuth: true

or if you use credentials, omit the npmAuthToken and use yarn npm login --scope someScope. This will add the token to the global file.

You have to completely remove npmScopes from the project's yarnrc.yml. Because the local file takes precedence and if the section (npmScopes) is found, it replaces the same section from the global file. As the token is stored in the global file (to avoid committing it to the repo), the authentication fails as it is never supplied.

Related