oven-sh / bun

Incredibly fast JavaScript runtime, bundler, test runner, and package manager – all in one
https://bun.sh
Other
74.24k stars 2.77k forks source link

"bun install" inside the monorepo installs all "node_modules" from "packages" into the root folder #5688

Open Dugnist opened 1 year ago

Dugnist commented 1 year ago

What version of Bun is running?

1.0.2+37edd5a6e389265738e89265bcbdf2999cb81a49

What platform is your computer?

Linux 6.2.0-32-generic x86_64 x86_64 Ubuntu 22.04.3 LTS

What steps can reproduce the bug?

root package.json:

{
  "name": "monorepo",
  "private": "true",
  "version": "0.0.1",
  "type": "module",
  "workspaces": [
    "packages/*"
  ],
}

I have the packages/one and packages/two structure.

Each package.json look like this:

{
  "name": "one",
  "private": true,
  "version": "0.0.1",
  "module": "index.ts",
  "type": "module",
  "dependencies": {
    "bun-types": "latest",
    "zod": "1"
  }
}

What is the expected behavior?

When I run "bun install" -> I expect to have separated node_modules for each package.

What do you see instead?

When I run "bun install" -> I see shared node_modules for all packages inside a root of a project

Additional information

I write a code to install node_modules from inside each package but it also made a root node_modules folder:

import { promisify } from "node:util";
import { exec } from "node:child_process";

const execAsync = promisify(exec);

// Get list of files inside packages folder
import { getInsideFolderNames } from "../lib/get-project-folder-names/index.ts";

const { listOfPackages, packagesFolderPath } = await getInsideFolderNames(
  "packages"
);

for await (const packageName of listOfPackages) {
  try {
    const packagePath = packagesFolderPath + "/" + packageName;

    const goInsidePackageAndInstallCommand = (
      await execAsync(`cd ${packagePath} && ls -a && bun install`)
    ).stdout;

    console.log(goInsidePackageAndInstallCommand);
  } catch (error: any) {
    console.warn("Ignore: ", error.message);
  }
}
colinhacks commented 1 year ago

Unless I'm missing something specific about your situation, this is precisely how workspaces are supposed to work. If all of your packages share dependencies, they get hoisted to the root level. Part of the appeal is that you don't need to install shared dependencies into each individual sub-package. https://www.jonathancreamer.com/inside-the-pain-of-monorepos-and-hoisting/

Try this with Yarn or pnpm and you should see the same thing.

Dugnist commented 1 year ago

@colinhacks in my case, "node_modules" folders are not created inside any package at all. Only the "node_modules" folder at the root of the project. One of the packages uses "fastify", so it definitely has unique dependencies that should not be moved up.

After running pnpm, everything is installed correctly.

btw thanks for the article - it's very useful information)

notramo commented 1 year ago

A bigger problem is that the bun.lockb is messed up. E.g. when installing inside workspace, the root lockfile is overwritten to contain the deps from workspace/package.json, disregarding root package.json entirely.

aldo-roman commented 1 year ago

@colinhacks While this is useful for most projects, it is needed to have a way to override this.

For instance, MedusaJS project requires node_modules in its own directory

ryoppippi commented 1 year ago

@notramo This happens to me. Please make a separate issue about that. I cannot use bun for production because of that

huilensolis commented 9 months ago

hi, my mono repo has an API with bun and a frontend with next js. The packages were installed on the project root. I got errors when I deployed to vercel because some packages of the API used common JS and next js doesn't support it.

after switching to pnpm everything works fine.

mkosir commented 7 months ago

Any news or feedback on this? It's the only thing thats keeps me switching monorepo from pnpm to bun.

janwirth commented 7 months ago

I also would like to have the node_modules in the directory of the app in order to be able to use expo with bun.

Cygnusfear commented 7 months ago

+1 for using Bun with Foundry in a monorepo

jonOsm commented 5 months ago

seeing a similiar issue with using react-router-dom my monorepo's frontend folder

janwirth commented 5 months ago

I actually don't have this problem anymore, using bun with t3-turbo which includes expo and nextJS

WillsterJohnson commented 2 months ago

This is still an issue. I'm getting typescript errors in Zed when I import a linked (via workspace:*) local package in a monorepo. The language server doesn't know everything that Bun knows, so it can't find the package even though Bun can without any problems. We absolutely need a node_modules directory in every project directory, even if it's just full of symlinks.

Speaking of a node_modules directory in every project directory full of symlinks, here's a (very awful) script I wrote to get around this issue. Your mileage may vary for your use case, but at a very basic level it emulates what pnpm does and seems to solve a few problems.