yarnpkg / yarnpkg/berry

[Bug?]: yarn removes custom dependency grouping from `package.json` during `yarn install`

Open
#6,348 1 comment 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

bug
Dominant language
TypeScript
Stars
8.1k
Forks
1.3k
PR merge metrics
No merged PRs in 30d

Description

Self-service
  • I'd be willing to implement a fix
Describe the bug

I have a package.json that I've organised to keep the dependencies grouped (based on keeping the vanilla react-native dependencies separate from our custom ones, to help with upgrading). I've upgraded this to use yarn 3.6.4 and now when I run yarn install (even if the current node_modules is in sync with the yarn.lock, so effectively a no-op) the listings for dependencies and devDependencies are reordered alphabetically, with any manual grouping stripped out.

My expectation is that the package.json file is respected in all ways as much as possible, including formatting, and it feels like this is a regression from previous versions of yarn.

To reproduce

Starting with a package.json like so:

{
  "name": "example",
  "version": "0.0.1",
  "private": true,
  "scripts": {
    "android": "react-native run-android",
    "ios": "react-native run-ios",
    "lint": "eslint .",
    "start": "react-native start",
    "test": "jest",

    "postinstall": "patch-package"
  },
  "dependencies": {
    "react": "18.2.0",
    "react-native": "0.74.2",

    "@react-native-async-storage/async-storage": "1.23.1",
    "@react-native-community/datetimepicker": "8.0.1",
    "@react-native-community/netinfo": "11.3.1",
    "@react-navigation/native": "~6.0.13",
    "@react-navigation/stack": "~6.3.2",
    "Base64": "^1.1.0",
    "deprecated-react-native-prop-types": "~4.1.0",
    "lodash": "^4.17.15",
    "moment": "^2.24.0",
    "moment-range": "^4.0.2",
    "rc-swipeout": "~2.0.11",
    "react-native-animatable": "^1.3.3",
    "react-native-blob-util": "~0.18.3",
    "react-native-camera": "~4.2.1",
    "react-native-draggable-flatlist": "~4.0.1",
    "react-native-elements": "~2.1.0",
    "react-native-fs": "~2.18.0",
    "react-native-gesture-handler": "~2.16.1",
    "react-native-image-picker": "2.3.0",
    "react-native-keyboard-aware-scroll-view": "~0.9.5",
    "react-native-linear-gradient": "^2.5.6",
    "react-native-markdown-renderer": "^3.2.8",
    "react-native-modal-selector": "~2.0.9",
    "react-native-orientation-locker": "1.4.0",
    "react-native-pdf": "~6.6.2",
    "react-native-reanimated": "~3.10.1",
    "react-native-safe-area-context": "4.10.1",
    "react-native-screens": "3.31.1",
    "react-native-signature-capture": "^0.4.10",
    "react-native-svg": "15.2.0",
    "react-native-svg-charts": "^5.3.0",
    "react-native-table-component": "~1.2.2",
    "react-native-vector-icons": "~9.2.0",
    "react-native-video": "~5.2.1",
    "react-native-webview": "13.8.6",
    "react-redux": "~7.2.9",
    "redux": "^4.0.4",
    "redux-persist": "^6.0.0",
    "redux-persist-filesystem-storage": "~4.2.0"
  },
  "devDependencies": {
    "@babel/core": "^7.20.0",
    "@babel/preset-env": "^7.20.0",
    "@babel/runtime": "^7.20.0",
    "@react-native/babel-preset": "0.74.84",
    "@react-native/eslint-config": "0.74.84",
    "@react-native/metro-config": "0.74.84",
    "@react-native/typescript-config": "0.74.84",
    "@types/react": "^18.2.6",
    "@types/react-test-renderer": "^18.0.0",
    "babel-jest": "^29.6.3",
    "eslint": "^8.19.0",
    "jest": "^29.6.3",
    "prettier": "2.8.8",
    "react-test-renderer": "18.2.0",
    "typescript": "5.0.4",

    "@babel/plugin-transform-class-properties": "~7.22.5",
    "@babel/plugin-transform-private-methods": "~7.22.5",
    "@testing-library/jest-native": "^5.4.2",
    "@testing-library/react-native": "^7.2.0",
    "babel-eslint": "^10.1.0",
    "eslint-plugin-react": "^7.20.6",
    "eslint-plugin-react-native": "~4.0.0",
    "patch-package": "~7.0.0"
  },
  "engines": {
    "node": ">=18"
  },
  "packageManager": "yarn@3.6.4"
}

run yarn install, which modifies package.json to:

{
  "name": "example",
  "version": "0.0.1",
  "private": true,
  "scripts": {
    "android": "react-native run-android",
    "ios": "react-native run-ios",
    "lint": "eslint .",
    "start": "react-native start",
    "test": "jest",
    "postinstall": "patch-package"
  },
  "dependencies": {
    "@react-native-async-storage/async-storage": "1.23.1",
    "@react-native-community/datetimepicker": "8.0.1",
    "@react-native-community/netinfo": "11.3.1",
    "@react-navigation/native": "~6.0.13",
    "@react-navigation/stack": "~6.3.2",
    "Base64": "^1.1.0",
    "deprecated-react-native-prop-types": "~4.1.0",
    "lodash": "^4.17.15",
    "moment": "^2.24.0",
    "moment-range": "^4.0.2",
    "rc-swipeout": "~2.0.11",
    "react": "18.2.0",
    "react-native": "0.74.2",
    "react-native-animatable": "^1.3.3",
    "react-native-blob-util": "~0.18.3",
    "react-native-camera": "~4.2.1",
    "react-native-draggable-flatlist": "~4.0.1",
    "react-native-elements": "~2.1.0",
    "react-native-fs": "~2.18.0",
    "react-native-gesture-handler": "~2.16.1",
    "react-native-image-picker": "2.3.0",
    "react-native-keyboard-aware-scroll-view": "~0.9.5",
    "react-native-linear-gradient": "^2.5.6",
    "react-native-markdown-renderer": "^3.2.8",
    "react-native-modal-selector": "~2.0.9",
    "react-native-orientation-locker": "1.4.0",
    "react-native-pdf": "~6.6.2",
    "react-native-reanimated": "~3.10.1",
    "react-native-safe-area-context": "4.10.1",
    "react-native-screens": "3.31.1",
    "react-native-signature-capture": "^0.4.10",
    "react-native-svg": "15.2.0",
    "react-native-svg-charts": "^5.3.0",
    "react-native-table-component": "~1.2.2",
    "react-native-vector-icons": "~9.2.0",
    "react-native-video": "~5.2.1",
    "react-native-webview": "13.8.6",
    "react-redux": "~7.2.9",
    "redux": "^4.0.4",
    "redux-persist": "^6.0.0",
    "redux-persist-filesystem-storage": "~4.2.0"
  },
  "devDependencies": {
    "@babel/core": "^7.20.0",
    "@babel/plugin-transform-class-properties": "~7.22.5",
    "@babel/plugin-transform-private-methods": "~7.22.5",
    "@babel/preset-env": "^7.20.0",
    "@babel/runtime": "^7.20.0",
    "@react-native/babel-preset": "0.74.84",
    "@react-native/eslint-config": "0.74.84",
    "@react-native/metro-config": "0.74.84",
    "@react-native/typescript-config": "0.74.84",
    "@testing-library/jest-native": "^5.4.2",
    "@testing-library/react-native": "^7.2.0",
    "@types/react": "^18.2.6",
    "@types/react-test-renderer": "^18.0.0",
    "babel-eslint": "^10.1.0",
    "babel-jest": "^29.6.3",
    "eslint": "^8.19.0",
    "eslint-plugin-react": "^7.20.6",
    "eslint-plugin-react-native": "~4.0.0",
    "jest": "^29.6.3",
    "patch-package": "~7.0.0",
    "prettier": "2.8.8",
    "react-test-renderer": "18.2.0",
    "typescript": "5.0.4"
  },
  "engines": {
    "node": ">=18"
  },
  "packageManager": "yarn@3.6.4"
}
Environment
System:
    OS: macOS 14.5
    CPU: (12) arm64 Apple M2 Pro
  Binaries:
    Node: 18.20.2 - /private/var/folders/_g/kc3wz03n2mb32x9ty7m6sh9m0000gn/T/xfs-0956b883/node
    Yarn: 3.6.4 - /private/var/folders/_g/kc3wz03n2mb32x9ty7m6sh9m0000gn/T/xfs-0956b883/yarn
    npm: 9.9.3 - /opt/local/bin/npm
  npmPackages:
    jest: ^29.6.3 => 29.7.0
Additional context

No response

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start by reproducing the behavior with the provided package.json and Yarn 3.6.4 using yarn install, confirming the dependency groups are reordered even when installation is otherwise a no-op. Trace the install path that writes package.json; done means custom dependency ordering and grouping remain unchanged after installation.

Written by the indexing model from the issue text.

Assessment

Tech stack
nodejs, typescript
Domain
tooling
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
42/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.