这是indexloc提供的服务,不要输入任何密码
Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
157 changes: 45 additions & 112 deletions docs/repo-docs/guides/migrating-from-nx.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -12,19 +12,21 @@ This guide will help you migrate an existing Nx repository to Turborepo.

## Why switch?

There are several reasons why you might want to switch from from Nx to Turborepo.
### Specific Focus

### Ecosystem standards
Turborepo is focused on TypeScript and JavaScript packages [built on top of package manager workspaces](/repo/docs/crafting-your-repository/structuring-a-repository). If this matches your focus, you may find it easier to navigate Turborepo's set of features and documentation to find what you are looking for.

Turborepo is [built on top of package manager workspaces](/repo/docs/crafting-your-repository/structuring-a-repository), meaning more tools and workflows are likely to work without plugins or other workarounds. By comparison, the default Nx starter uses conventions and strategies unique to Nx, and you can expect to write more Nx-only code as your codebase grows.
### Vercel Interoperability

### More control of source code
If you are already a part of the Vercel ecosystem, for example using the infrastructure provided by us, then you will feel right at home with Turborepo.

Nx’s philosophy involves wrapping your code with layers of plugins, other dependencies, and Nx-specific code. Instead, Turborepo infers your repository’s needs from its structure and source code. Since your source code goes through fewer layers of abstraction to be analyzed, you maintain greater control of your repository.
We provide dedicated [Remote Caching](/repo/docs/core-concepts/remote-caching) options for all Turborepo users, where we store the results of your task on a cloud server. This saves enormous amounts of time by **preventing duplicated work across your entire organization**. [Vercel Remote Cache](https://vercel.com/docs/monorepos/remote-caching) has saved teams over 500 years of compute so far.
Comment on lines +19 to +23
Copy link
Contributor

@anthonyshew anthonyshew Feb 19, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm having a hard time seeing how Turborepo working great on Vercel is relevant to this doc. While true, this documentation is meant for folks migrating from Nx to Turborepo. It doesn't have anything to do with Vercel, nor should it. It's very possible that someone could be getting acquainted with Turborepo for the first time on this document, and this section would be misleading for them.

I don't know how else to read these edits other than a projection about the way Nx has been closing off the open-source parts of its offering, according to what Nx users have been repeatedly telling me. I don't write this to be rude or antagonistic, but I can't tell what these edits are meant to be for and am having to guess.

We take great pride in creating an open-source project that anyone can use how they wish. As fate would have it, this morning we just finished up some improvements for self-hosting (ref and ref) and I've been working on creating an OpenAPI spec viewer for our docs the past week or so.

Were you meaning something else/I'm not getting it?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm sorry if it wasn't clear in the video, but in it I tried to relay the following: I am not an expert on Turborepo, and so this was an honest attempt by me to provide additional, objective steelman arguments as to why you might want to switch.

As I demonstrated, some of the existing arguments needed to be removed completely due to their inaccuracy, so I wanted to offer up ideas for replacements that I felt were honest and objective (again with the caveat that I am not deep enough to know all of the potential benefits of Turborepo and they are therefore high level starting points for discussion).

If you disagree with this point and don't want it included that's totally fine, and I'm sure you can come up with other points to replace it (do feel free to commit directly to the branch if you want to).

Vercel famously makes a ton of open-source tooling, so I am not really sure what the link is there with what you're saying and why you thought it was a negative thing, it wasn't intended to be one.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds good! I illustrated how the spirit of those sections should stay here, so let's refocus there.


### Less configuration
### Less global configuration

Migrating to Turborepo will likely require deleting previous configuration needed for Nx. Turborepo will automatically infer much of what your repository needs. For example, here are the tool-specific configurations you'll find in the default starters for Turborepo and Nx.
Nx maintains explicit global configuration (i.e. entries in `nx.json`) in cases where Turborepo prefers implicit defaults. This is again applicable because of Turborepo's narrower focus on TypeScript and JavaScript packages and often means that `turbo.json` files have fewer lines in them than `nx.json` files. This preference for less explicit configuration is not mirrored at the package level, however, where explicit npm scripts are required by Turborepo, whereas Nx infers them via its plugins that are wired up at the global level (in `nx.json`).

For example, here are the tool-specific configurations you'll find in the default starter for Turborepo, and the equivalent Nx preset for developing Next.js applications (with inferred tasks for building, typechecking with TypeScript project references, serving and linting). Nx does not need this level of configuration to work like Turborepo does, but this is the way Nx is recommended to be configured.

<Tabs items={["Turborepo", "Nx"]}>

Expand Down Expand Up @@ -66,50 +68,43 @@ Migrating to Turborepo will likely require deleting previous configuration neede
"production": [
"default",
"!{projectRoot}/.eslintrc.json",
"!{projectRoot}/eslint.config.cjs",
"!{projectRoot}/**/?(*.)+(spec|test).[jt]s?(x)?(.snap)",
"!{projectRoot}/tsconfig.spec.json",
"!{projectRoot}/jest.config.[jt]s",
"!{projectRoot}/src/test-setup.[jt]s",
"!{projectRoot}/test-setup.[jt]s"
"!{projectRoot}/eslint.config.mjs"
],
"sharedGlobals": ["{workspaceRoot}/.github/workflows/ci.yml"]
"sharedGlobals": []
},
"nxCloudId": "6789ec521d90a2165398f39a",
"plugins": [
{
"plugin": "@nx/next/plugin",
"plugin": "@nx/js/typescript",
"options": {
"startTargetName": "start",
"buildTargetName": "build",
"devTargetName": "dev",
"serveStaticTargetName": "serve-static"
"typecheck": {
"targetName": "typecheck"
},
"build": {
"targetName": "build",
"configName": "tsconfig.lib.json",
"buildDepsName": "build-deps",
"watchDepsName": "watch-deps"
}
}
},
{
"plugin": "@nx/playwright/plugin",
"plugin": "@nx/next/plugin",
"options": {
"targetName": "e2e"
"startTargetName": "start",
"buildTargetName": "build",
"devTargetName": "dev",
"serveStaticTargetName": "serve-static",
"buildDepsTargetName": "build-deps",
"watchDepsTargetName": "watch-deps"
}
},
{
"plugin": "@nx/eslint/plugin",
"options": {
"targetName": "lint"
}
},
{
"plugin": "@nx/jest/plugin",
"options": {
"targetName": "test"
}
}
],
"targetDefaults": {
"e2e-ci--**/*": {
"dependsOn": ["^build"]
}
},
"generators": {
"@nx/next": {
"application": {
Expand All @@ -121,34 +116,12 @@ Migrating to Turborepo will likely require deleting previous configuration neede
}
```

```json title="project.json"
{
"name": "starter",
"$schema": "../../node_modules/nx/schemas/project-schema.json",
"sourceRoot": "apps/starter",
"projectType": "application",
"tags": [],
"// targets": "to see all targets run: nx show project starter --web",
"targets": {}
}
```

</Tab>

</Tabs>

### Free Remote Caching
Copy link

@Jordan-Hall Jordan-Hall Feb 19, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've not watched the video in full maybe their an explanation. I love NX and I know nx offer "free license" but I think this section should remain as it's not the same and for Enterprise its a paid license.

Lot of the rest fair just thisnsection removal seems strange

Copy link
Contributor

@anthonyshew anthonyshew Feb 19, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is an explanation given in the video, but I'm having the hardest time understanding it.

An explicit reason for this section getting written has been an influx of new users to Turborepo, coming from Nx, because of a change in the cost structure of using Nx. They're finding that features that they used to use for free aren't free anymore.

Note that this is specifically not my experience or something I went out of my way to invent. This is written how it is because of experiences other developers have shared with me. The first couple times I heard it, I went to read the docs about how the pricing is meant to work, and was confused by the explanations and documentation given. In one place it would sound like its part of the open-source offering, and the next would sound like it isn't.

I continually pestered the people I was talking to about this, and insisted that maybe they were misunderstanding the documentation (hoping that their familiarity with the tool or Nx team would lead me to concluding that the feature is still free), but they repeated that it was the case that they were losing features.

From the conversations I've had, questions I've answered, and frequency at which this comes up, I don't see any other option than having to mention this paradigm in this documentation.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ive been extremely vocal around this with NX. Many still feel like the free license not enough and their no way to run remote cache without it being a NX licensed software. I've got a hot patch but once it goes to rust it's nesr impossible


Turborepo’s [Remote Caching](/repo/docs/core-concepts/remote-caching) stores the results of your task on a cloud server. This saves enormous amounts of time by **preventing duplicated work across your entire organization**. [Vercel Remote Cache](https://vercel.com/docs/monorepos/remote-caching) has saved teams over 500 years of compute so far.

Since Nx 19.7, similar functionality is a paid-for feature, even when self-hosting. Remote Caching with Turborepo is free when [self-hosting](/repo/docs/core-concepts/remote-caching#self-hosting) or using [Vercel Remote Cache](https://vercel.com/docs/monorepos/remote-caching).

## Migration steps

Our goal for this migration is to get a working Turborepo task as quickly as possible, so that you can adopt Turborepo features incrementally. We’ll start by using the Nx scaffolder to create a repository with a Next.js app.

```bash title="Terminal"
npx create-nx-workspace --preset=next --ci=skip --e2eTestRunner=none --style=tailwind --nextAppDir=true --nextSrcDir=false --packageManager=pnpm --appName=starter
npx create-nx-workspace --workspaces --preset=next --ci=skip --e2eTestRunner=none --unitTestRunner=none --style=tailwind --nextAppDir=true --nextSrcDir=false --appName=starter
Copy link
Contributor

@anthonyshew anthonyshew Feb 19, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can see why these changes to start with a JS Workspace would make sense without context. I did it without a Workspace because everyone I've had to help with a migration comes from a place of being misaligned with the JS ecosystem due to the recommendations of the Nx documentation. Without fail, we have to introduce the Workspace first, and then we continue with the rest.

Would you want to take another try at it to make the doc say something to the effect of "If you already are using Workspaces, you can skip steps x, y, and z"? A banner above this code block would likely work great!

Copy link
Contributor Author

@JamesHenry JamesHenry Feb 20, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I do feel like inflammatory language like "misaligned with the JS ecosystem" isn't particularly helpful to the discourse. I don't think the countless monorepos out there deriving enormous value from the setup that Nx originally started with (before the prevalence of package manager workspaces) deserve such a derogatory label. We still provide support for this/them, in addition to package manager workspaces. You have to remember your sampling bias here, it is exclusively folks who are already dissatisfied that are going through this with you.

I'm not fully picturing what you're proposing but I think it sounds reasonable, maybe I could take a look at the change if you make it please?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What you've quoted is not inflammatory language. I can understand that you might not like it, but it's purely a technical comment. If you told me something in Turborepo isn't aligned with the ecosystem in some way, I would thank you and do my best to fix it. The JS ecosystem has aligned on Workspaces and the majority of the subset of Nx users that come to Turborepo don't use them, to their detriment.

You have to remember your sampling bias here, it is exclusively folks who are already dissatisfied that are going through this with you.

I'm well aware of this. This page's contents are specifically written as a collection of their feedback.

```

### Step 1: Update .gitignore
Expand All @@ -159,71 +132,31 @@ Turborepo uses the .turbo directory to hold local caches and other information a
.turbo
```

### Step 2: Add a workspace definition

Turborepo is built on top of package manager workspaces, a JavaScript ecosystem standard. Add the directory paths to the workspace that will contain packages.

<PackageManagerTabs>

<Tab>

```json title="package.json"
{
"workspaces": ["apps/*"]
}
```

</Tab>

<Tab>

```json title="package.json"
{
"workspaces": ["apps/*"]
}
```
### Step 2: Remove Nx plugin

</Tab>
Remove the Nx plugin from ./apps/starter/next.config.js. The example file below doesn’t have configuration, though your existing Next.js application may need some.

<Tab>
```js title="./apps/starter/next.config.js"
/** @type {import('next').NextConfig} */
const nextConfig = {};

```yml title="pnpm-workspace.yaml"
packages:
- apps/*
module.exports = nextConfig;
```

</Tab>

</PackageManagerTabs>

### Step 3: Add a package.json to the application

Rather than adding additional configuration files like `project.json`, Turborepo uses the standard `package.json` file.
### Step 3: Add explicit scripts to the package.json of the application

Add a `package.json` to the `starter` application. Create a `package.json` at `./apps/starter/package.json` that contains a `dev` and `build` script.
Nx's Next.js plugin inferred the scripts for the application, but Turborepo uses explicit npm scripts, so we add them like so:

```json title="./apps/starter/package.json"
{
"name": "starter",
"scripts": {
"dev": "next dev",
"build": "next build"
}
}
```

### Step 4: Remove Nx plugin

Remove the Nx plugin from ./apps/starter/next.config.js. The example file below doesn’t have configuration, though your existing Next.js application may need some.

```js title="./apps/starter/next.config.js"
/** @type {import('next').NextConfig} */
const nextConfig = {};

module.exports = nextConfig;
```

### Step 5: Add the `packageManager` field
### Step 4: Add the `packageManager` field

The root package.json needs to have the `packageManager` field. This ensures developers in the repository use the correct package manager, and that Turborepo can optimize your package graph based on your lockfile.

Expand Down Expand Up @@ -261,7 +194,7 @@ The root package.json needs to have the `packageManager` field. This ensures dev

</PackageManagerTabs>

### Step 6: Run you package manager's install command
### Step 5: Run you package manager's install command

Update your lockfile by running your installation command.

Expand Down Expand Up @@ -295,7 +228,7 @@ pnpm install

Once you've done this, you should see a lockfile diff, indicating that the package has been added to the package manager's workspace.

### Step 7: Install Turborepo
### Step 6: Install Turborepo

Add Turborepo to the root `package.json` of the workspace.

Expand Down Expand Up @@ -357,9 +290,9 @@ pnpm install turbo --global

</PackageManagerTabs>

### Step 8: Add a `turbo.json`
### Step 7: Add a `turbo.json`

Create a `turbo.json` at the root to register your tasks and describe their task dependencies.
Create a `turbo.json` at the root to register your tasks and describe their task dependencies. Note, this does not yet cover the same functionality as was in the original `nx.json` and is an example of getting started quickly with a subset of capabilities.
Copy link
Contributor

@anthonyshew anthonyshew Feb 19, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you say what tasks or configuration are missing?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure yeah, again this is regarding the argument that Nx requires "more configuration" and this felt like it wasn't clearly established as being intentionally not "apples to apples".

Here in Step 7 you have a tasks configuration that only deals with building and serving the Next.js application, whereas the nx.json we start the process with covers building, serving (both from source and from dist), typechecking and linting.


```json title="./turbo.json"
{
Expand All @@ -376,7 +309,7 @@ Create a `turbo.json` at the root to register your tasks and describe their task
}
```

### Step 9: Run `turbo build`
### Step 8: Run `turbo build`

Build the application with Turborepo. Using global `turbo`, this would be `turbo build`. You can also run the command through your package manager:

Expand Down Expand Up @@ -408,7 +341,7 @@ pnpm exec turbo build

</PackageManagerTabs>

### Step 10: Enable Remote Caching (optional)
### Step 9: Enable Remote Caching (optional)

By default, Turborepo will connect to the free-to-use Vercel Remote Cache when you run:

Expand All @@ -433,7 +366,7 @@ We encourage incremental migration, meaning you will have both of Nx and Turbore

### Installing dependencies where they're used

Turborepo recommends [installing packages where they're used](/repo/docs/crafting-your-repository/managing-dependencies#best-practices-for-dependency-installation) to improve cache hit ratios, help dependency pruning capability, and clarify for developers which dependencies are meant for which packages. This is different from the Nx strategy, where all dependencies are installed at the root of the repository, making all dependencies available to all packages in the workspace.
Turborepo recommends [installing packages where they're used](/repo/docs/crafting-your-repository/managing-dependencies#best-practices-for-dependency-installation) to improve cache hit ratios, help dependency pruning capability, and clarify for developers which dependencies are meant for which packages.

Once you have tasks running through Turborepo, we highly recommend that you move dependencies to the `package.json`'s for packages and applications that need them. [Visit our documentation on managing dependencies](/repo/docs/crafting-your-repository/managing-dependencies) to learn more.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Once you have tasks running through Turborepo, we highly recommend that you move dependencies to the `package.json`'s for packages and applications that need them. [Visit our documentation on managing dependencies](/repo/docs/crafting-your-repository/managing-dependencies) to learn more.
Historically, Nx has recommended installing all dependencies in the root of the repository, making all dependencies available to all packages in the workspace. If you followed this guidance, we highly recommend that you move dependencies to the `package.json`'s for packages and applications that need them. [Visit our documentation on managing dependencies](/repo/docs/crafting-your-repository/managing-dependencies) to learn more.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you


Expand Down
Loading