Rush Stack商店部落格活動
跳到主要內容

偏好版本

背景

Rush 會為您的所有專案執行單一安裝,方法是在您的 common 資料夾中建立一個虛擬的 rush-common 專案,該專案會參考包含每個專案相依性的 tarball。 例如,假設您的 rush.json 有兩個專案 "project1" 和 "project2"。產生的檔案可能如下所示

common/temp/package.json

{
"name": "rush-common",
"description": "Temporary file generated by the Rush tool",
"private": true,
"version": "0.0.0",
"dependencies": {
"@rush-temp/project1": "file:./projects/project-1.tgz",
"@rush-temp/project2": "file:./projects/project-2.tgz"
}
}

套件管理員會將這些 "@rush-temp" 範圍的專案視為 rush-common 專案的直接相依性。 一般而言,NPM 會先安裝專案的直接相依性 (在 node_modules 樹狀結構的根目錄),然後才下載間接相依性。 但是由於您實際專案的直接相依性現在是 rush-common 專案的間接相依性,因此 npm install 行為可能會有所不同。

假設 project-1/package.json 看起來像這樣

{
"name": "project-1",
"version": "1.0.0",
"dependencies": {
"library-a": "1.0.1",
"library-b": "1.1.3"
}
}

假設 library-a (來自網際網路) 看起來像這樣

{
"name": "library-a",
"version": "1.0.1",
"dependencies": {
"library-b": "^1.0.0"
}
}

如果您在 project-1 中執行正常的 npm install,您會預期會有一個 node_modules 資料夾看起來像這樣,即使 library-b@1.4.4 存在於 NPM 登錄中

node_modules/
library-a/ (1.0.1)
library-b/ (1.1.3)

即使 library-b@1.4.4 符合 "^1.0.0" SemVer 模式,NPM 也不會安裝它,因為 1.1.3 (由 project-1 安裝) 已經滿足它。

但是,上述的 common/temp/package.json 不會保證這一點。 相反地,根據 project-2 的相依性,您可能會得到這個結果

node_modules/
project-1/
library-b/ (1.1.3)
library-a/ (1.0.1)
library-b/ (1.4.4)

... 這也是 SemVer 方程式的有效解決方案。 使用 Rush 與 NPM 的 同層級相依性時,可能會發生類似的問題。

偏好版本

為了控制這些影響,Rush 引入了「偏好版本」的概念,這些相依性會明確新增至最上層的 common/temp/package.json

您可以將版本新增至組態檔 common-versions.json 來「釘選」版本。 例如

common/config/rush/common-versions.json

{
"$schema": "https://developer.microsoft.com/json-schemas/rush/v5/common-versions.schema.json",
"preferredVersions": {
"css-loader": "1.2.3"
}
}

這會導致 css-loader 從我們上面的範例中新增至 common/temp/package.json,如下所示

{
"name": "rush-common",
"description": "Temporary file generated by the Rush tool",
"private": true,
"version": "0.0.0",
"dependencies": {
"css-loader": "1.2.3",
"@rush-temp/project1": "file:./projects/project-1.tgz",
"@rush-temp/project2": "file:./projects/project-2.tgz"
}
}

注意:如果您要發佈套件,您應該小心新增偏好版本,以免產生與正常使用 NPM 安裝您的程式庫的使用者不同的結果。

隱含偏好版本

依預設,Rush 會自動將您所有專案的所有直接相依性新增至 common/temp/package.json。 在我們原始的範例中,這些「隱含偏好版本」可能會像這樣出現

common/temp/package.json

{
"name": "rush-common",
"description": "Temporary file generated by the Rush tool",
"private": true,
"version": "0.0.0",
"dependencies": {
"css-loader": "1.2.3", // <---- preferred version that was specified above
"library-a": "~1.0.0", // <---- implicitly preferred version
"library-b": "1.1.3", // <---- implicitly preferred version
"@rush-temp/project1": "file:./projects/project-1.tgz",
"@rush-temp/project2": "file:./projects/project-2.tgz",
}
}

Rush 會為您執行此操作,除非在不同專案為給定的相依性指定不同的版本範圍時。 在這種情況下,Rush 不會知道應該隱含地偏好哪個版本。 例如,如果 project1project2 要求 library-b 的不同版本,那麼您可能需要介入,並可能使用 common-versions.json 來解決您的問題。

對於較舊的套件管理員,自動新增這些項目往往會減少間接相依性的重複。 不過,隱含偏好版本可能會為具有不相容 peerDependencies 範圍的某些相依性帶來麻煩。 如果您遇到與同層級相依性相關的安裝錯誤,我們建議您在 common/config/rush/common-versions.json 組態檔中將 implicitlyPreferredVersions 設定為 false 來停用此行為。