¿Cómo anulo las versiones de dependencia de NPM anidadas?

Resuelto georgebrock asked hace 11 años • 12 respuestas

Me gustaría utilizar el grunt-contrib-jasminepaquete NPM. Tiene varias dependencias. Parte del gráfico de dependencia se ve así:

─┬ grunt-contrib-jasmine@0.4.1
 │ ├─┬ grunt-lib-phantomjs@0.2.0
 │ │ ├─┬ phantomjs@1.8.2-2

Desafortunadamente, hay un error en esta versión phantomjsque impide que se instale correctamente en Mac OS X. Esto se solucionó en la última versión.

¿ Cómo puedo grunt-lib-phantomjsutilizar una versión más reciente de phantomjs?

Algún contexto adicional:

  • grunt-contrib-jasminerequiere explícitamente la versión "~0.2.0"de grunt-lib-phantomjs, que requiere explícitamente la versión "~1.8.1"de phantomjs.
  • Agregar phantomjsprimero las dependencias de mi paquete no tiene ningún efecto; ambas versiones están instaladas y grunt-contrib-jasminetodavía usan las versiones anteriores (consulte: Al instalar un paquete con NPM, ¿puede indicarle que use una versión diferente de una de sus dependencias? ).
georgebrock avatar Apr 04 '13 15:04 georgebrock
Aceptado

A partir de npm cli v8.3.0 (09/12/2021), esto se puede resolver utilizando el overridescampo package.json . Como se describe en la respuesta de StriplingWarrior

Por ejemplo, el proyecto tiene typescriptuna versión 4.6.2como dependencia directaawesome-typescript-loader de desarrollo y utiliza una versión anterior 2.7de typescript. Así es como puedes saber npmsi usar la versión 4.6.2de typescriptfor awesome-typescript-loader:

{
  "name": "myproject",
  "version": "0.0.0",
  "scripts": ...
  "dependencies": ...
  "devDependencies": {
    "typescript": "~4.6.2",
    "awesome-typescript-loader": "^5.2.1",
    ...
  },
  "overrides": {
    "awesome-typescript-loader": {
      "typescript": "$typescript"
    }
  }
}

Si no lo utiliza typescriptcomo dependencia de desarrollo directa , debe escribir 4.6.2en lugar de $typescripten la overridessección:

{
  "name": "myproject",
  "version": "0.0.0",
  "scripts": ...
  "dependencies": ...
  "devDependencies": {
    "awesome-typescript-loader": "^5.2.1",
    ...
  },
  "overrides": {
    "awesome-typescript-loader": {
      "typescript": "~4.6.2"
    }
  }
}

Para usar la última versión de la dependencia:

{
  "name": "myproject",
  "version": "0.0.0",
  "scripts": ...
  "dependencies": ...
  "devDependencies": {
    "awesome-typescript-loader": "^5.2.1",
    ...
  },
  "overrides": {
    "awesome-typescript-loader": {
      "typescript": "latest"
    }
  }
}

Lo mismo overridesse puede utilizar para ambos dependenciesy devDependencies.


Si está utilizando la versión npm >5 pero <8.3.0: edite su package-lock.json: elimine la biblioteca de "requires"la sección y agréguela en "dependencias".

Por ejemplo, desea que deglobel paquete utilice globla versión del paquete 3.2.11en lugar de la actual. Abres package-lock.jsony ves:

"deglob": {
  "version": "2.1.0",
  "resolved": "https://registry.npmjs.org/deglob/-/deglob-2.1.0.tgz",
  "integrity": "sha1-TUSr4W7zLHebSXK9FBqAMlApoUo=",
  "requires": {
    "find-root": "1.1.0",
    "glob": "7.1.2",
    "ignore": "3.3.5",
    "pkg-config": "1.1.1",
    "run-parallel": "1.1.6",
    "uniq": "1.0.1"
  }
},

Quitar "glob": "7.1.2",de "requires", agregar "dependencies"con la versión adecuada:

"deglob": {
  "version": "2.1.0",
  "resolved": "https://registry.npmjs.org/deglob/-/deglob-2.1.0.tgz",
  "integrity": "sha1-TUSr4W7zLHebSXK9FBqAMlApoUo=",
  "requires": {
    "find-root": "1.1.0",
    "ignore": "3.3.5",
    "pkg-config": "1.1.1",
    "run-parallel": "1.1.6",
    "uniq": "1.0.1"
  },
  "dependencies": {
    "glob": {
      "version": "3.2.11"
    }
  }
},

Ahora elimine su node_modulescarpeta, ejecútela npm ci(o npm installpara la versión anterior de node/npm) y agregará las partes faltantes a la "dependencies"sección.


izogfif avatar Jan 30 '2018 15:01 izogfif

Puede utilizar la funcionalidad npm encogimiento para anular cualquier dependencia o subdependencia.

Acabo de hacer esto en un gruntproyecto nuestro. Necesitábamos una versión más nueva de connect, ya que 2.7.3. nos estaba causando problemas. Entonces creé un archivo llamado npm-shrinkwrap.json:

{
  "dependencies": {
    "grunt-contrib-connect": {
      "version": "0.3.0",
      "from": "[email protected]",
      "dependencies": {
        "connect": {
          "version": "2.8.1",
          "from": "connect@~2.7.3"
        }
      }
    }
  }
}

npmdebería recogerlo automáticamente mientras realiza la instalación del proyecto.

(Ver: https://nodejs.org/en/blog/npm/managing-node-js-dependencies-with-shrinkwrap/ )

tuxpiper avatar Jul 02 '2013 11:07 tuxpiper

A partir de npm v8.3 (lanzado con Node.js 16 ), la forma correcta de solucionar esto es a través de la overridessección de su package.jsonarchivo.

Si necesita realizar cambios específicos en las dependencias de sus dependencias, por ejemplo, reemplazar la versión de una dependencia con un problema de seguridad conocido, reemplazar una dependencia existente con una bifurcación o asegurarse de que se use la misma versión de un paquete en todas partes, entonces puede agregar una anulación.

Las anulaciones proporcionan una manera de reemplazar un paquete en su árbol de dependencias con otra versión o con otro paquete completo. Estos cambios pueden tener un alcance tan específico o vago como se desee.

Para asegurarse de que el paquete foo siempre esté instalado como versión 1.0.0 sin importar en qué versión dependan sus dependencias:

{
  "overrides": {
    "foo": "1.0.0"
  }
}

Hay una variedad de otras configuraciones más matizadas que le permiten anular un paquete solo cuando depende de una jerarquía de paquetes particular. Para obtener más detalles, consulte https://docs.npmjs.com/cli/v9/configuring-npm/package-json#overrides

StriplingWarrior avatar Dec 17 '2021 16:12 StriplingWarrior

La única solución que funcionó para mí (nodo 12.x, npm 6.x) fue usar npm-force-solving desarrollado por @Rogerio Chaves .

Primero, instálelo mediante:

npm install npm-force-resolutions --save-dev

Puede agregar --ignore-scriptssi algunos scripts de dependencia transitiva rotos le impiden instalar algo.

Luego, package.jsondefina qué dependencia se debe anular (debe establecer el número de versión exacto ):

"resolutions": {
  "your-dependency-name": "1.23.4"
}

y en "scripts"la sección agregue una nueva entrada de preinstalación:

"preinstall": "npm-force-resolutions",

Ahora, npm installaplicará cambios y forzará your-dependency-namela versión 1.23.4para todas las dependencias.

user11153 avatar Jul 17 '2020 14:07 user11153