docs(nx-dev): migrating more blog posts (#29807)
@ -0,0 +1,174 @@
|
|||||||
|
---
|
||||||
|
title: 'Distributing CI: Binning and Distributed Task Execution'
|
||||||
|
slug: 'distributing-ci-binning-and-distributed-task-execution'
|
||||||
|
authors: ['Victor Savkin']
|
||||||
|
cover_image: '/blog/images/2021-06-15/jFVfKEglfQIM9QsP.png'
|
||||||
|
tags: [nx]
|
||||||
|
description: "In this post we looked at two ways to distribute your CI: binning and using Nx Cloud's distributed task execution."
|
||||||
|
---
|
||||||
|
|
||||||
|
As your Nx workspaces grow, running CI on a single agent becomes unworkable. Nx’s code change analysis and computation caching allows you to do the minimum amount of computation needed to verify that the PR is good to merge, but it only helps with the average case CI time. No matter how smart Nx is, in the worst case you need to rebuild/retest everything. **That’s why any sizable workspace has to distribute CI across multiple agents.**
|
||||||
|
|
||||||
|
In this post we look at two ways to do that.
|
||||||
|
|
||||||
|
## Approach 1: Binning
|
||||||
|
|
||||||
|
Binning is an approach to distribution where the planning job divides the work into equally-weighted bins, one for each worker job. Then every worker executes the work prepared for it.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
Nx has always provided affordances to do that, and many workspaces took advantage of it. Most of the setups look similar. This is an [example of implementing binning using Azure Pipelines](/ci/recipes/set-up/monorepo-ci-azure).
|
||||||
|
|
||||||
|
The planning job invokes _print-affected_. This command executes the same logic as _“affected:\*”_ but instead of running the tasks, it returns the tasks’ descriptions. The job invokes this command for each target such as build/test/lint/e2e. After that, each worker agent runs the tasks assigned to it.
|
||||||
|
|
||||||
|
Binning is very common. For instance, [the CircleCI support for running tests in parallel](https://circleci.com/docs/2.0/parallelism-faster-jobs/) uses binning.
|
||||||
|
|
||||||
|
We at Nrwl helped many large companies distribute CI using different variations of binning. It works reasonably well for simple cases, but not without issues.
|
||||||
|
|
||||||
|
## Issues with Binning
|
||||||
|
|
||||||
|
### Binning doesn’t partition the work in the optimal way.
|
||||||
|
|
||||||
|
First, you cannot partition tasks into bins without knowing how long every task takes. Most binning solutions collect timings (including the one in the Azure example above) which works imperfectly.
|
||||||
|
|
||||||
|
Second, when using binning you split tasks of the same type: some agents run tests, some agents run lints. If you have a fixed set of agents, you often have a situation where one group of agents (say executing lints) finishes before the other group (say executing tests). **You cannot balance them well.**
|
||||||
|
|
||||||
|
Additionally, you have to clone the repo and restore installed dependencies three times, consequently: once for planning, once for testing, and once for deployment. If this step takes 3 minutes, you have a 9-minute setup cost.
|
||||||
|
|
||||||
|
### Binning splits semantic commands into many chunks.
|
||||||
|
|
||||||
|
If you partition your tests into five bins, you have five agents with separate log files. When some of them fail, you have to go through all the logs to see what has happened. Even though this is not a deal-breaker, in a large workspace with dozens of agents executing every CI run, this becomes a real issue.
|
||||||
|
|
||||||
|
More importantly, you often need all the file outputs for a given target on the same machine to do post-processing. For instance, **you can run the tests on 5 agents, but you need all the coverage reports in the same place to combine them and send them to SonarQube.** Doing this is challenging.
|
||||||
|
|
||||||
|
### Binning doesn’t work for builds.
|
||||||
|
|
||||||
|
Any time you run a command in a monorepo, Nx creates a task graph, which it then executes.
|
||||||
|
|
||||||
|
**The biggest limitation of binning is that it only works when the task graph is a list.** The moment you have dependencies between tasks, you have to distribute tasks dynamically using some sort of coordinator, move the needed files between agents and so forth.
|
||||||
|
|
||||||
|
This is common when you have libraries that depend on other libraries.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
In this example, the Child 1 and Child 2 libraries have to be built first. Parent 1 can start only when Child 1 has been built because it needs the Child 1’s dist folder. Parent 2 has to wait for both Child 1 and Child 2. And they can all be built on different agents, so their dist folders will have to be moved from agent to agent. You cannot implement it using binning. This problem also occurs for tests that require the libraries or applications to be built first.
|
||||||
|
|
||||||
|
That’s why you often see tool authors talking about distributing tests and not builds. **Distributing tests is relatively straightforward. Distributing builds is hard.**
|
||||||
|
|
||||||
|
### Binning complicates CI/CD Setup.
|
||||||
|
|
||||||
|
Maintaining a CI setup that uses binning is often an ongoing effort. Because you don’t have a proper coordinator, your CI has to be the coordinator, which complicates things.
|
||||||
|
|
||||||
|
## Approach 2: Nx Cloud 2.0 Distributed Task Execution (DTE)
|
||||||
|
|
||||||
|
We at Nrwl are in the business of helping companies use monorepos, so we have been dealing with these issues for many years. Nx Cloud 2.0’s support for Distributed Task Execution is our solution for this problem. It solves all the problems listed above and more.
|
||||||
|
|
||||||
|
## How Does Distributed Task Execution Work?
|
||||||
|
|
||||||
|
This is an example CircleCI configuration that runs all commands on a single agent.
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
jobs:
|
||||||
|
main:
|
||||||
|
environment:
|
||||||
|
steps:
|
||||||
|
- setup # clones the repo and runs npm install
|
||||||
|
- run: npx nx affected --target=test --parallel --maxParallel=3
|
||||||
|
- run: npx nx affected --target=lint --parallel --maxParallel=3
|
||||||
|
- run: npx nx affected --target=e2e
|
||||||
|
- run: npx nx affected --target=build
|
||||||
|
workflows:
|
||||||
|
PR:
|
||||||
|
jobs:
|
||||||
|
- main
|
||||||
|
```
|
||||||
|
|
||||||
|
Now use DTE to run the commands using 3 separate agents.
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
jobs:
|
||||||
|
main:
|
||||||
|
environment:
|
||||||
|
NX_CLOUD_DISTRIBUTED_EXECUTION: "true"
|
||||||
|
steps:
|
||||||
|
- setup
|
||||||
|
- run: npx nx affected --target=test --parallel --maxParallel=3
|
||||||
|
- run: npx nx affected --target=lint --parallel --maxParallel=3
|
||||||
|
- run: npx nx affected --target=e2e
|
||||||
|
- run: npx nx affected --target=build
|
||||||
|
- run: npx nx-cloud stop-all-agents
|
||||||
|
agent:
|
||||||
|
steps:
|
||||||
|
- setup
|
||||||
|
- run:
|
||||||
|
name: Agent
|
||||||
|
command: npx nx-cloud start-agent
|
||||||
|
workflows:
|
||||||
|
PR:
|
||||||
|
jobs:
|
||||||
|
- agent
|
||||||
|
name: agent1
|
||||||
|
- agent
|
||||||
|
name: agent2
|
||||||
|
- agent
|
||||||
|
name: agent3
|
||||||
|
- main
|
||||||
|
```
|
||||||
|
|
||||||
|
As you can see there is not much that changed. We added the agent job, registered it 3 times, added the `NX_CLOUD_DISTRIBUTED_EXECUTION` env variable, and added an extra step to stop all the agents. That is it.
|
||||||
|
|
||||||
|
**What happens when it runs `nx affected --build`?**
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
It won’t run the build locally. Instead, it sends the Task Graph to Nx Cloud. Nx Cloud Agents pick up the tasks they can run and execute them.
|
||||||
|
|
||||||
|
> The Nx Cloud agents here are CI jobs that run `npx nx-cloud start-agent` so they can can be defined in any CI env.
|
||||||
|
|
||||||
|
This happens transparently. If an agent builds `app1`, it fetches the outputs for lib if it doesn’t have it already.
|
||||||
|
|
||||||
|
As agents complete tasks, the main job where you invoked `nx affected --build` l starts receiving created files and terminal outputs.
|
||||||
|
|
||||||
|
After `nx affected --build` completes, the main job has the built artifacts and all the terminal outputs as if it ran it locally.
|
||||||
|
|
||||||
|
Let’s reexamine the issues above to see how we addressed them.
|
||||||
|
|
||||||
|
### Nx Cloud partitions the work in the optimal way.
|
||||||
|
|
||||||
|
In theory every agent could pull one task at a time to partition things evenly, but it doesn’t work well in practice. The network overhead can add up for very small tasks, and it’s often faster to run several tasks in parallel because of the batching capabilities Nx has.
|
||||||
|
|
||||||
|
As you run commands in your repo, Nx Cloud collects the timings and uses those to partition the work into well-sized batches, such that if one agent is slow, the CI isn’t blocked. Agents also run tasks of different types (tests/lints), so the pool of agents is shared evenly.
|
||||||
|
|
||||||
|
### Nx Cloud does not split commands.
|
||||||
|
|
||||||
|
To stress one more time the main job contains all the terminal outputs and all the files from all the tasks that ran on the agents, as if it ran locally. There is one place to look for errors. The created Nx Cloud run will contain all the information from all the agents.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
**Finally, because all the files are copied into the main job, you can combine any outputs in post-processing steps, in exactly the same way you did it before enabling distribution.**
|
||||||
|
|
||||||
|
### Nx Cloud distributes builds.
|
||||||
|
|
||||||
|
**Nx Cloud is a proper coordinator and it can process any task graph**. An Nx Cloud agent asks for tasks to execute. The Nx Cloud service looks at the commands currently running and will see if there are any tasks that have no unfulfilled dependencies. If there are some, the Nx Cloud service will use the collected timings to create a well-size batch of tasks that it will send to the agent.
|
||||||
|
|
||||||
|
The agent sees if it has all the files required to run those tasks (`dist` folders from previous tasks). And if it doesn’t, it downloads them. When it’s done running the task, it lets the Nx Cloud service know to “unblock” other tasks in the graph. At the same time, the Nx Cloud service sends the created files and terminal outputs to the main job.
|
||||||
|
|
||||||
|
### Nx Cloud does not require you to rewrite the CI setup.
|
||||||
|
|
||||||
|
As you saw above, the CI setup, by and large, remained the same. And nothing had to change in the workspace itself. For instance, the `npx nx affected --target=test --parallel --maxParallel=3` command looks exactly the same. The meaning of `--max-parallel` changes its meaning from run up to 3 test tasks on the main job to run up to 3 test tasks on each agent.
|
||||||
|
|
||||||
|
If you want to change this command without distribution, add `NX_CLOUD_DISTRIBUTED_EXECUTION` as follows: `NX_CLOUD_DISTRIBUTED_EXECUTION=false npx nx affected --target=test --parallel --maxParallel=3`.
|
||||||
|
|
||||||
|
### Works With any CI System
|
||||||
|
|
||||||
|
When using distributed task execution all the communication is done from your agents to Nx Cloud. This means that it works with any CI system, including your private Jenkins installations. See some examples [here](/ci/recipes/set-up). And even works locally if you create a docker image from the state of repo and push it to say ECS. It also works with Nx Private Cloud.
|
||||||
|
|
||||||
|
## Summary
|
||||||
|
|
||||||
|
In this post we looked at two ways to distribute your CI: binning and using Nx Cloud’s distributed task execution.
|
||||||
|
|
||||||
|
Binning has been supported from Day 1 and works well for a variety of workspaces. It has drawbacks: the resource allocation, the developer ergonomics, the inability to distribute builds, and a much more complex Ci setup.
|
||||||
|
|
||||||
|
Nx Cloud distributed task execution addresses the drawbacks.
|
||||||
|
|
||||||
|
[Learn more about Nx Cloud 2.0 and its support for distributed task execution](/nx-cloud).
|
||||||
@ -0,0 +1,163 @@
|
|||||||
|
---
|
||||||
|
title: 'Nx 14.2 — Angular v14, Storybook update, lightweight Nx and more!'
|
||||||
|
slug: 'nx-14-2-angular-v14-storybook-update-lightweight-nx-and-more'
|
||||||
|
authors: ['Juri Strumpflohner']
|
||||||
|
cover_image: '/blog/images/2022-06-09/uScdSDGP4NgCKFrPdznbhw.png'
|
||||||
|
tags: [nx, release]
|
||||||
|
description: 'Another release packed with cool features and improvements just got released: Nx 14.2. Read all about the Angular v14 upgrade that comes with it, TypeScript and other 3rd party package upgrades, improved Angular CLI to Nx migrations, optional `nx.json` and speed improvements.'
|
||||||
|
---
|
||||||
|
|
||||||
|
Another release packed with cool features and improvements just got released: [Nx 14.2](https://github.com/nrwl/nx/releases/tag/14.2.2). Read all about the Angular v14 upgrade that comes with it, TypeScript and other 3rd party package upgrades, improved Angular CLI to Nx migrations, optional `nx.json` and speed improvements.
|
||||||
|
|
||||||
|
## Angular v14
|
||||||
|
|
||||||
|
Angular v14 just got released last week. Read all about [the news here](https://blog.angular.io/angular-v14-is-now-available-391a6db736af). Huge kudos and congrats to the Angular team for again shipping on time based on their 6 months major release cycle. We’ve been collaborating with the team closely over the last couple of weeks to test early RCs, give feedback about upcoming features and foremost, make sure the new version not only works great in Nx, but also in the broader ecosystem that Nx supports such as Jest, ESLint, Storybook, Cypress and more.
|
||||||
|
|
||||||
|
We’re excited about the new features that landed in Angular v14 which bring some fresh air and long-awaited innovations to the framework (\* cough \* Standalone Components, \* cough \* typed Angular forms).
|
||||||
|
|
||||||
|
As such, if you upgrade to Nx 14.2 (`npx nx migrate latest`), Nx will make sure to also trigger all the Angular v14 related migration scripts to update your workspace to the latest Angular version.
|
||||||
|
|
||||||
|
## TypeScript 4.7 and Prettier 2.6
|
||||||
|
|
||||||
|
With this release we also automatically update:
|
||||||
|
|
||||||
|
- TypeScript to version v4.7 ([announcement](https://devblogs.microsoft.com/typescript/announcing-typescript-4-7/))
|
||||||
|
- Prettier to v2.6 ([announcement](https://prettier.io/blog/2022/03/16/2.6.0.html))
|
||||||
|
|
||||||
|
## Storybook 6.5
|
||||||
|
|
||||||
|
Nx 14.2 upgrades Storybook to the latest 6.5 version automatically for you.
|
||||||
|
|
||||||
|
Storybook support has been in Nx for a long time and we had our custom executor (builder) to preconfigure Storybook in a way that it works best within an Angular monorepo setup. We’re glad that the Storybook support for Angular improved a lot over the last couple of releases s.t. we can **now directly use the Storybook native builders for Angular** (`@storybook/angular:start-storybook`, `@storybook/angular:build-storybook`). In your `project.json` (or `workspace.json` / `angular.json`) you should see the executor now being set to:
|
||||||
|
|
||||||
|
```json
|
||||||
|
"storybook": {
|
||||||
|
"executor": "@storybook/angular:start-storybook",
|
||||||
|
...
|
||||||
|
},
|
||||||
|
```
|
||||||
|
|
||||||
|
This avoids any potential downsides of options being different or not available and lowers the maintenance burden on our side going forward.
|
||||||
|
|
||||||
|
Storybook 6.5 also comes with support for using TS based Storybook configurations files, such as `main.ts` , `preview.ts` etc. We added support for that to our Storybook configuration generators.
|
||||||
|
|
||||||
|
For all the other cool Storybook features, please refer to their release [announcement](https://storybook.js.org/releases/6.5).
|
||||||
|
|
||||||
|
## Easy migration from Angular CLI to Nx
|
||||||
|
|
||||||
|
Nx is not only for large monorepos, but works really well for single-project Angular workspaces too! Why switch to Nx? We need an entire blog post for that (spoiler: coming soon 😉), but in a nutshell:
|
||||||
|
|
||||||
|
- everything from the Angular CLI still works
|
||||||
|
- you get faster builds, test runs, linting etc powered by Nx’s task scheduling and caching
|
||||||
|
- more schematics (we call them generators in Nx) with specific support for SCAM, NgRX setup, module federation and micro frontend setup and much more to come (looking at you Standalone Components)
|
||||||
|
- better, out of the box integration with community tools such as Jest for unit testing, ESLint, Cypress, Storybook,…
|
||||||
|
- improved developer experience powered by the [Nx Console VSCode extension](/getting-started/editor-setup)
|
||||||
|
- …
|
||||||
|
|
||||||
|
In the last couple of weeks we’ve been working hard on making an automated migration from the Angular CLI to Nx as seamless as it can possibly get. And this can be tricky, believe us. We always had automated migrations, but we improved our existing ones and in addition also added support for multi-project Angular CLI workspaces.
|
||||||
|
|
||||||
|
All you need to do is to run the following command on your existing Angular CLI setup.
|
||||||
|
|
||||||
|
```
|
||||||
|
ng add @nrwl/angular
|
||||||
|
```
|
||||||
|
|
||||||
|
We try to infer your current setup and configuration and automatically migrate it, in addition to providing useful warnings and logs for the things we couldn’t migrate along the way, such that you have the possibility to manually adjust things.
|
||||||
|
|
||||||
|
## More lightweight Nx
|
||||||
|
|
||||||
|
When you setup a new Nx workspace you can choose from a variety of presets (templates) that preconfigure your workspace in the best possible way, already setting up tool like Prettier, Jest, ESLint and Cypress. For some folks however, this might seem too much.
|
||||||
|
|
||||||
|
For that, Nx always already had the — what we call — “Nx Core” setup. You can read more about [that on our guide](/getting-started/intro), but it basically allows Nx to be used without its plugins, just for the fast, powerful task scheduling and caching capabilities.
|
||||||
|
|
||||||
|
In v14 we already simplified Nx (we have a whole section in [our release blog post](/blog/nx-v14-is-out-here-is-all-you-need-to-know)) and in v14.2 we even go a step further: **we made `nx.json` optional**, providing some reasonable defaults. Now, if you want to add Nx’s powerful task scheduler to an existing repository, all you need to do is to add the `nx` package as a dependency and you’re all set up.
|
||||||
|
|
||||||
|
Whenever you need to fine-tune the default settings you can run the following command to get a `nx.json` generated or you can obviously create it by hand:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx init
|
||||||
|
```
|
||||||
|
|
||||||
|
## Run Nx graph on any monorepo!
|
||||||
|
|
||||||
|
Speaking about lightweight Nx. With Nx v14.2.3 you can now just run
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx graph
|
||||||
|
```
|
||||||
|
|
||||||
|
to download the Nx package, have it analyze your monorepo’s project graph and visualize it in its powerful project graph UI. Give it a try. Here’s Victor demoing it on the Next.js and Babel.js repository!
|
||||||
|
|
||||||
|
{% tweet url="https://twitter.com/victorsavkin/status/1534909897976041474" /%}
|
||||||
|
|
||||||
|
## Nx just got faster, again!
|
||||||
|
|
||||||
|
Part of our team has been heads-down on Lerna in the past month since we [took over stewardship of Lerna](/blog/lerna-is-dead-long-live-lerna). And apart from releasing Lerna 5 with important package upgrades, we wanted to solve Lerna’s biggest pain point: being slow. [We published an article](/blog/lerna-used-to-walk-now-it-can-fly) on how we envision that strategy 2 weeks ago and as part of that we’ve been digging deep into the Nx core and have been doing some proper profiling.
|
||||||
|
|
||||||
|
The result: Nx itself got faster as well 😃.
|
||||||
|
|
||||||
|
Here’s the result of running our benchmark using the latest version of Nx 14.2:
|
||||||
|
|
||||||
|
```plaintext
|
||||||
|
* average lage time is: 10203.6
|
||||||
|
* average turbo time is: 1532.3
|
||||||
|
* average lerna (powered by nx) time is: 272.2
|
||||||
|
* average nx time is: 194.8
|
||||||
|
* nx is 52.379876796714576x faster than lage
|
||||||
|
* nx is 7.866016427104722x faster than turbo
|
||||||
|
* nx is 1.3973305954825461x faster than lerna (powered by nx)
|
||||||
|
```
|
||||||
|
|
||||||
|
(as always, feel free to [reproduce it here](https://github.com/vsavkin/large-monorepo))
|
||||||
|
|
||||||
|
## Dedicated Linting support for Nx Plugins
|
||||||
|
|
||||||
|
Only the possibility of being able to tailor and customize the processes and behavior of your monorepo tooling to your own needs, makes working with it pleasant and allows you to get most out of it. Whether it is to customize the code generation aspect to your company coding styleguide and best practices, to automate the setup of new projects or even add support for languages such as Go, .Net or Flutter. [Nx Plugins](/community) enable such support and really help you make Nx work in the best possible way for your current scenario.
|
||||||
|
|
||||||
|
Nx plugin support has been around for a while. Just have a look at our [Nx community plugins page](/community). And we keep improving it. We added support for [Nx Plugin presets](https://www.youtube.com/watch?v=yGUrF0-uqaU) and [lately also the ability for local plugins](/blog/nx-v14-is-out-here-is-all-you-need-to-know). In this release, we add proper **linting support for Nx Plugin development**.
|
||||||
|
|
||||||
|
Ever happened to you that you mistyped the implementation file in your `generators.json` configuration file of your plugin? Well guess what, now the linting process would warn you about:
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
When you generate a new Nx plugin, you should now have a `@nrwl/nx/nx-plugin-checks` configuration in your `.eslintrc.json` file.
|
||||||
|
|
||||||
|
```json
|
||||||
|
{
|
||||||
|
"files": ["./package.json", "./generators.json", "./executors.json"],
|
||||||
|
"parser": "jsonc-eslint-parser",
|
||||||
|
"rules": {
|
||||||
|
"@nrwl/nx/nx-plugin-checks": "error"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
If you have an existing plugin, you can run the following generator to add the new lint rules:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx g @nrwl/nx-plugin:plugin-lint-checks --projectName=awesomeplugin
|
||||||
|
```
|
||||||
|
|
||||||
|
## How to Update Nx
|
||||||
|
|
||||||
|
Updating Nx is done with the following command, and will update your Nx workspace dependencies and code to the latest version:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx migrate latest
|
||||||
|
```
|
||||||
|
|
||||||
|
After updating your dependencies, run any necessary migrations.
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx migrate --run-migrations
|
||||||
|
```
|
||||||
|
|
||||||
|
## Exciting?
|
||||||
|
|
||||||
|
We’re already deep into following our v15 [roadmap](https://github.com/nrwl/nx/discussions/9716) with a lot of cool stuff coming up on the horizon.
|
||||||
|
|
||||||
|
Makes sure you don’t miss anything by
|
||||||
|
|
||||||
|
- Following us [on Twitter](https://twitter.com/NxDevTools), and
|
||||||
|
- Subscribe to the [YouTube Channel](https://youtube.com/nrwl_io?sub_confirmation=1) for more information on [Angular](https://angular.io/), [React](https://reactjs.org/), Nx, and more!
|
||||||
|
- Subscribing to [our newsletter](https://go.nx.dev/nx-newsletter)!
|
||||||
@ -0,0 +1,200 @@
|
|||||||
|
---
|
||||||
|
title: 'Nx 14.4 — Inputs, optional npm scope, project graph cache directory and more!'
|
||||||
|
slug: 'nx-14-4-inputs-optional-npm-scope-project-graph-cache-directory-and-more'
|
||||||
|
authors: ['Juri Strumpflohner']
|
||||||
|
cover_image: '/blog/images/2022-07-05/lpmHhIiE9v5yJI6nLi2dlw.png'
|
||||||
|
tags: [nx, release]
|
||||||
|
description: 'Our last release blog post has been published not even a month ago and we already released 2 more minors. You missed the releases? No worries, we’ve got you covered. Here’s all you need to know.'
|
||||||
|
---
|
||||||
|
|
||||||
|
Our [last release blog post](/blog/nx-14-2-angular-v14-storybook-update-lightweight-nx-and-more) has been published not even a month ago and we already released 2 more minors. You missed the releases? No worries, we’ve got you covered. Here’s all you need to know.
|
||||||
|
|
||||||
|
## targetDependencies -> targetDefaults
|
||||||
|
|
||||||
|
To get things started, `targetDependencies` got renamed to `targetDefaults`. We originally named them `targetDependencies` because you were able to define dependencies among project targets (e.g. to run the `build` target of dependent projects). See the next section for some more info about that.
|
||||||
|
|
||||||
|
You could always do more though. However, with our current mission to reduce configuration duplication, the now-called `targetDefaults` will get more powerful by allowing you to define sensible defaults for your project configs in a central place.
|
||||||
|
|
||||||
|
> _Don’t worry, if you’re using `nx migrate` it'll handle the rewriting for you._
|
||||||
|
|
||||||
|
## Syntactic sugar for “dependsOn”
|
||||||
|
|
||||||
|
One of the key features of the Nx task scheduling system is that it is able to automatically build/test/lint/{name your operation} dependencies of your project. If you have `proj-a` which has a dependency on `proj-b` and we run `nx build proj-a` then Nx automatically builds `proj-b` before building `proj-a`. Why? Because `proj-a` depends on the output of `proj-b`.
|
||||||
|
|
||||||
|
These target defaults can be defined
|
||||||
|
|
||||||
|
- globally at the `nx.json` level for all the projects in the workspace
|
||||||
|
- per project level in the `project.json`/`package.json` depending whether you use the [project.json config option](/reference/project-configuration) or [package.json](/reference/project-configuration)
|
||||||
|
|
||||||
|
You can still use the same notation as you did until now:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"dependsOn": [
|
||||||
|
{
|
||||||
|
"target": "build",
|
||||||
|
"projects": "dependencies"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
...
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
With this release we introduce another, much more concise and elegant way of expressing the same:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"dependsOn": ["^build"]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
...
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Similarly, if you don’t specify the `^` it would be the same as writing the following:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"dependsOn": [
|
||||||
|
{
|
||||||
|
"target": "prebuild",
|
||||||
|
"projects": "self"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
...
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
In that case target `prebuild` on the project itself is invoked before running its `build` target.
|
||||||
|
|
||||||
|
## Inputs, Named Inputs, ENV and runtime variables
|
||||||
|
|
||||||
|
In order to improve cache hits we added the possibility to define `inputs`. For example on the `build` target, you could define the following input glob pattern to avoid cache invalidation when only spec files got changed.
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"inputs": ["!{projectRoot}/**/*.spec.ts"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
You can have as many inputs as you like. Also, in order to avoid ambiguity when specifying the path, you need to use either `{projectRoot}` or `{workspaceRoot}` in the glob pattern.
|
||||||
|
|
||||||
|
Since you might want to **reuse certain patterns across multiple targets**, we also introduced `namedInputs`, which allows you to define a set of patterns that can then be referenced in the various `targetDefaults`:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"namedInputs": {
|
||||||
|
"prodFiles": ["!{projectRoot}/**/*.spec.ts"]
|
||||||
|
},
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"inputs": ["prodFiles", "^prodFiles"]
|
||||||
|
},
|
||||||
|
"publish": {
|
||||||
|
"inputs": ["prodFiles", "^prodFiles"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Note, by also adding `^` in front of the named input pattern, it also gets applied to all dependent projects, just like with the `dependsOn` definition.
|
||||||
|
|
||||||
|
**Inputs can not only just be file globs, but also runtime or environment variables**. This makes the `inputs` even more powerful and helps improve cache hits. In the following example, the environment variable "SELECTED_CLI", as well as the runtime output of running `node -v` would be included in the computation of the hash used for storing the cached result.
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"targetDefaults": {
|
||||||
|
"e2e": {
|
||||||
|
"inputs": [
|
||||||
|
{
|
||||||
|
"env": "SELECTED_CLI"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"runtime": "node -v"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
> _Note that `targetDefaults` is just a way to specify project-specific settings in a central place within the `nx.json`. All of these can directly also be added to the `package.json` or `project.json` (depending on which approach you use for configuring your projects)._
|
||||||
|
|
||||||
|
Check out the following video which goes into some of the details on the example of a [Lerna](https://lerna.js.org/) monorepo that uses the new Nx inputs configuration.
|
||||||
|
|
||||||
|
{% youtube src="https://youtu.be/u91YHPwddEM" /%}
|
||||||
|
|
||||||
|
## Optional npmScope
|
||||||
|
|
||||||
|
When you create a new Nx workspace it sets up a “npm scope” which you can find in the `nx.json`.
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
"npmScope": "myorg",
|
||||||
|
...
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Although most of the time you might want to use one, it is not mandatory any more. This contributes to our mission of simplifying Nx and making it more flexible.
|
||||||
|
|
||||||
|
## Speeding up workspace config computation
|
||||||
|
|
||||||
|
Project configuration calculations can take up quite some time in large workspaces. Starting with v14.4 we offloaded that part to the [Nx Daemon](/concepts/nx-daemon), optimizing the overall command execution time in particular for large workspaces.
|
||||||
|
|
||||||
|
## New NX_PROJECT_GRAPH_CACHE_DIRECTORY
|
||||||
|
|
||||||
|
When using shared volumes on CI, different consumers of the cache can write a different project graph to the cache, thus overwriting one that may be in use by other consumers. Up until now, there was no way to specify a different cache directory just for the project graph.
|
||||||
|
|
||||||
|
With this release, we introduce a new `NX_PROJECT_GRAPH_CACHE_DIRECTORY` environment variable to dictate where Nx (and the Nx Daemon) should store the project graph cache.
|
||||||
|
|
||||||
|
## Angular updates
|
||||||
|
|
||||||
|
In Nx v14.2 we [also shipped the Angular v14 migrations](/blog/nx-14-2-angular-v14-storybook-update-lightweight-nx-and-more) which went smoothly. We keep improving our support. In this release in particular we
|
||||||
|
|
||||||
|
- added support to generate Storybook stories also for Angular standalone components
|
||||||
|
- upgraded `@angular-eslint/*` to version 14
|
||||||
|
- added support for `ngrx` version 14
|
||||||
|
|
||||||
|
## How to Update Nx
|
||||||
|
|
||||||
|
Updating Nx is done with the following command, and will update your Nx workspace dependencies and code to the latest version:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx migrate latest
|
||||||
|
```
|
||||||
|
|
||||||
|
After updating your dependencies, run any necessary migrations.
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx migrate --run-migrations
|
||||||
|
```
|
||||||
|
|
||||||
|
## Exciting?
|
||||||
|
|
||||||
|
We’re already deep into following our v15 [roadmap](https://github.com/nrwl/nx/discussions/9716) with a lot of cool stuff coming up on the horizon.
|
||||||
|
|
||||||
|
Makes sure you don’t miss anything by
|
||||||
|
|
||||||
|
- Following us [on Twitter](https://twitter.com/NxDevTools), and
|
||||||
|
- Subscribe to the [YouTube Channel](https://youtube.com/nrwl_io?sub_confirmation=1) for more information on [Angular](https://angular.io/), [React](https://reactjs.org/), Nx, and more!
|
||||||
|
- Subscribing to [our newsletter](https://go.nx.dev/nx-newsletter)!
|
||||||
@ -0,0 +1,304 @@
|
|||||||
|
---
|
||||||
|
title: 'Nx 14.5 — Cypess v10, Output globs, Linter perf, React Tailwind support'
|
||||||
|
slug: 'nx-14-5-cypress-v10-output-globs-linter-perf-react-tailwind-support'
|
||||||
|
authors: ['Juri Strumpflohner']
|
||||||
|
cover_image: '/blog/images/2022-08-02/ZUzLD-4JgrEBIZb3dXOvag.png'
|
||||||
|
tags: [nx, release]
|
||||||
|
description: 'Here we go! After not even a month of releasing v14.4, Nx v14.5 is out!! Here’s all you need to know.'
|
||||||
|
---
|
||||||
|
|
||||||
|
Here we go! After not even a month of [releasing v14.4](/blog/nx-14-4-inputs-optional-npm-scope-project-graph-cache-directory-and-more), Nx v14.5 is out!! Here’s all you need to know.
|
||||||
|
|
||||||
|
**TL;DR:** [https://github.com/nrwl/nx/releases/tag/14.5.0](https://github.com/nrwl/nx/releases/tag/14.5.0)
|
||||||
|
|
||||||
|
## Cypress v10 and Component Testing
|
||||||
|
|
||||||
|
Cypress v10 is probably the most significant update since Cypress was released. It comes with a new, exciting [Cypress App](https://docs.cypress.io/guides/core-concepts/cypress-app), component testing beta, a new JS/TS-based configuration file and much more. Read all the details in [their official announcement](https://www.cypress.io/blog/2022/06/01/cypress-10-release/).
|
||||||
|
|
||||||
|
One of the strengths of Nx is to integrate various tools into a cohesive, high-quality experience. Working together with other companies and open source projects is key to making sure we meet this goal. We have had an ongoing relationship with the folks over at Cypress for years already and have been working closely with them since earlier this year to integrate v10 into Nx in the best possible way.
|
||||||
|
|
||||||
|
This includes an upgrade script to automatically migrate Nx users using Cypress v9 seamlessly to v10. By running…
|
||||||
|
|
||||||
|
```shell
|
||||||
|
nx g @nrwl/cypress:migrate-to-cypress-10
|
||||||
|
```
|
||||||
|
|
||||||
|
…your workspace will be automatically upgraded to the latest Cypress version.
|
||||||
|
|
||||||
|
Cypress v10 also comes with a beta version of [Component Testing](https://docs.cypress.io/guides/component-testing/writing-your-first-component-test). Nx v14.5 comes with an integrated generator to add component testing support to React-based project:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
nx g @nrwl/react:cypress-component-configuration --project=my-react-project --generate-tests
|
||||||
|
```
|
||||||
|
|
||||||
|
You can also append the `--generate-tests` to automatically generate Cypress component tests for the existing components in the target project (`my-react-project`).
|
||||||
|
|
||||||
|
```shell
|
||||||
|
nx g @nrwl/react:cypress-component-configuration --project=my-react-project --generate-tests
|
||||||
|
```
|
||||||
|
|
||||||
|
Check out our [generator docs](/nx-api/react/generators/cypress-component-configuration) for more info.
|
||||||
|
|
||||||
|
{% youtube src="https://youtu.be/QDWN4C7T-Ck" /%}
|
||||||
|
|
||||||
|
## Globs for Task Outputs
|
||||||
|
|
||||||
|
In v14.4 we [introduced inputs and namedInputs](/blog/nx-14-4-inputs-optional-npm-scope-project-graph-cache-directory-and-more). They allow you to fine-tune how caching works and when it should be invalidated.
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"inputs": ["!{projectRoot}/**/*.spec.ts"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Specifying such inputs can drastically increase the number of cache hits!
|
||||||
|
|
||||||
|
{% tweet url="https://twitter.com/victorsavkin/status/1550187124678205440" /%}
|
||||||
|
|
||||||
|
In this release, we also allow specifying globs for `outputs`. Outputs are optional as Nx comes with reasonable defaults, but you can specify your own if your setup differs from the most commonly used ones:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
...
|
||||||
|
"outputs": ["dist/libs/mylib"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Globs are particularly useful when multiple targets write to the same directory. Say you have a `build-js` and `build-css` command and both write into `dist/libs/mylib`. For reasons of clarity, if possible, our recommendation is to split them up. Like:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
"build-js": {
|
||||||
|
"outputs": ["dist/libs/mylib/js"]
|
||||||
|
},
|
||||||
|
"build-css": {
|
||||||
|
"outputs": ["dist/libs/mylib/css"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Sometimes that’s not feasible though. In that case, globs come in handy:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
"build-js": {
|
||||||
|
"outputs": ["dist/libs/mylib/**/*.js"]
|
||||||
|
},
|
||||||
|
"build-css": {
|
||||||
|
"outputs": ["dist/libs/mylib/**/*.css"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
[Read more in our docs](/reference/project-configuration)
|
||||||
|
|
||||||
|
## Parameter Forwarding when building dependent projects
|
||||||
|
|
||||||
|
Besides the speed aspect, one key feature of Nx is the ability to build dependent projects automatically. Let’s say you have `project-a` which depends on `project-b`, then whenever you run the build for `project-a`, thanks to its project graph, Nx will automatically run the build for `project-b` first. You can define such dependencies either directly in your [project.json](/reference/project-configuration) or [package.json](/reference/project-configuration) file, or globally for an entire workspace in `nx.json`:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"dependsOn": ["^build"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
The `^` is a short-hand notation for
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"dependsOn": [{ "projects": "dependencies", "target": "build" }]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
...and defines that the `build` task should be run for all its dependencies first.
|
||||||
|
|
||||||
|
> _You have a PNPM,NPM or Yarn workspace? Adding Nx doesn’t only benefit you in terms of speed improvements, but also to define such build dependencies. Have a look at this video to learn more:_ [_Setup a monorepo with PNPM workspaces and add Nx for speed: Defining task dependencies aka build pipelines_](https://youtu.be/ngdoUQBvAjo?t=1485)
|
||||||
|
|
||||||
|
What happens to parameters when invoking the target on a project’s dependencies? By default, they are not forwarded but starting with 14.5 you can. Here are some configuration options:
|
||||||
|
|
||||||
|
```json
|
||||||
|
"build": {
|
||||||
|
// forward params passed to this target to the dependency targets
|
||||||
|
"dependsOn": [
|
||||||
|
{ "projects": "dependencies", "target": "build", "params": "forward" }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"test": {
|
||||||
|
// ignore params passed to this target, won't be forwarded to the dependency targets
|
||||||
|
"dependsOn": [
|
||||||
|
{ "projects": "self", "target": "build", "params": "ignore" }
|
||||||
|
]
|
||||||
|
}
|
||||||
|
"lint": {
|
||||||
|
// ignore params passed to this target, won't be forwarded to the dependency targets
|
||||||
|
"dependsOn": [
|
||||||
|
{ "projects": "self", "target": "build" }
|
||||||
|
]
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
[Read more in our docs](/reference/project-configuration)
|
||||||
|
|
||||||
|
## Linting Performance
|
||||||
|
|
||||||
|
We are obsessed with performance, yes we are! And I have good news: the Nx module boundary lint rule just got an order of magnitude faster 🤯.
|
||||||
|
|
||||||
|
{% tweet url="https://twitter.com/meeroslav/status/1550058325236191232" /%}
|
||||||
|
|
||||||
|
Replacing `Sets`, `foreach`, `reduce` with plain `for` loops can often have quite a significant impact. You won't notice much on smaller projects, but on large Nx workspaces with 500+ projects you should see some huge improvements 🚀.
|
||||||
|
|
||||||
|
## Support for banned external imports lint checks on transitive dependencies
|
||||||
|
|
||||||
|
The [Nx Module Boundary lint rule](/features/enforce-module-boundaries) is a powerful concept especially when it comes to the maintainability aspect of projects and monorepos. Learn more in our blog article on [Taming Code Organization with Module Boundaries in Nx](/blog/mastering-the-project-boundaries-in-nx).
|
||||||
|
|
||||||
|
The Module Boundary rule allows for much more though. It also allows to ban external imports. Say you have a frontend project where you want to make sure none of the “backend-type” dependencies accidentally get imported. Or vice-versa, a backend project where you wouldn’t necessarily want to depend on any “frontend-type” package references. You can use the `bannedExternalImports` for that. For example:
|
||||||
|
|
||||||
|
```json {% fileName=".eslintrc.json" %}
|
||||||
|
{
|
||||||
|
// ... more ESLint config here // nx-enforce-module-boundaries should already exist at the top-level of your config
|
||||||
|
"nx-enforce-module-boundaries": [
|
||||||
|
"error",
|
||||||
|
{
|
||||||
|
"allow": [],
|
||||||
|
// update depConstraints based on your tags
|
||||||
|
"depConstraints": [
|
||||||
|
// projects tagged with "frontend" can't import from "@nestjs/common"
|
||||||
|
{
|
||||||
|
"sourceTag": "frontend",
|
||||||
|
"bannedExternalImports": ["@nestjs/common"]
|
||||||
|
},
|
||||||
|
// projects tagged with "backend" can't import from "@angular/core"
|
||||||
|
{
|
||||||
|
"sourceTag": "backend",
|
||||||
|
"bannedExternalImports": ["@angular/core"]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
] // ... more ESLint config here
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Note, the `frontend` and `backend` `sourceTag` definition is something you define. You could have easily named it differently. It is a string that can be attached to a project by adding it to the `tag` property of its `project.json` configuration file. Read more about banned external imports [in our docs](/features/enforce-module-boundaries).
|
||||||
|
|
||||||
|
Starting with 14.5 we now support such checks also on transitive dependencies. Assume we have `project-a` and `project-b`, both of which are tagged as `framework-agnostic` and have `react` in their banned external imports. Also, assume there's a relationship like `project-a -> project-b`. If `project-b` imports `react` and we run linting, it fails correctly. However, if we run linting on `project-a`, it succeeds as `project-a` is not importing `react` at all, thus not breaking the lint rule. In most situations, this is fine because linting happens at a project level, but sometimes you might want to have a "transitive" behavior where linting would also fail for `project-a` because it imports `project-a` which imports `react`.
|
||||||
|
|
||||||
|
You can now enable such behavior by setting `checkNestedExternalImports` to `true`:
|
||||||
|
|
||||||
|
```json {% fileName=".eslintrc.json" %}
|
||||||
|
{
|
||||||
|
// ... more ESLint config here // nx-enforce-module-boundaries should already exist at the top-level of your config
|
||||||
|
"nx-enforce-module-boundaries": [
|
||||||
|
"error",
|
||||||
|
{
|
||||||
|
"allow": [],
|
||||||
|
"checkNestedExternalImports": true,
|
||||||
|
// update depConstraints based on your tags
|
||||||
|
"depConstraints": [
|
||||||
|
// projects tagged with "frontend" can't import from "@nestjs/common"
|
||||||
|
{
|
||||||
|
"sourceTag": "framework-agnostic",
|
||||||
|
"bannedExternalImports": ["react"]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
// ... more ESLint config here
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
## Improved automated Module Boundary Lint Rule fixes
|
||||||
|
|
||||||
|
In v13.10 we introduced automated fixes for the Nx Module Boundary rules. Wrong relative imports such as the following can be easily adjusted automatically by providing the `--fix` when running linting on the project.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
This is a huge time saver, especially on large projects. With Nx v14.5 the automated fixes now also support automated resolution of absolute imports across library boundaries, such as
|
||||||
|
|
||||||
|
```typescript
|
||||||
|
// WRONG
|
||||||
|
import { libSayHi } from 'libs/tslib-a/src/index';
|
||||||
|
|
||||||
|
// automatically fixed to
|
||||||
|
import { libSayHi } from '@myorg/tslib-a';
|
||||||
|
```
|
||||||
|
|
||||||
|
## Nx Migrate improvements and Nx Repair
|
||||||
|
|
||||||
|
We improved our log output from the Nx automated code migration run to make it more clear what a code migration actually changes. Also, those migrations that don’t do anything because they don’t apply to your workspace are not shown in the output at all.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
## Tailwind Setup Generator for React
|
||||||
|
|
||||||
|
It has never been easier to add [Tailwind](https://tailwindcss.com/) support to your React app or library. Just run the `setup-tailwind` generator:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx g @nrwl/react:setup-tailwind --project=<project-name>
|
||||||
|
```
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
This automatically sets up your project with a PostCSS and Tailwind configuration.
|
||||||
|
|
||||||
|
## React Native: Add Detox config to Expo apps
|
||||||
|
|
||||||
|
We also improved our React Native support by adding the possibility to generate a [Detox](https://wix.github.io/Detox/) config for Expo applications.
|
||||||
|
|
||||||
|
## Deprecating Angular Protractor e2e tests
|
||||||
|
|
||||||
|
[Protractor](https://github.com/angular/protractor/issues/5502) has been deprecated for a while on the Angular CLI side and given Nx has had [Cypress](https://cypress.io/) support for a while it has never been a popular choice. Starting with this release we’re deprecating the generator for setting up Protractor and we’re planning on removing support entirely in Nx v15.
|
||||||
|
|
||||||
|
## Other Package updates
|
||||||
|
|
||||||
|
Here are some more package updates that come with this release and will automatically be bumped when you run the Nx migration:
|
||||||
|
|
||||||
|
- Angular v14.1.0
|
||||||
|
- Express 14.18.1
|
||||||
|
- Nest v9
|
||||||
|
- Next.js v12.2.2
|
||||||
|
- React Native 0.69.1
|
||||||
|
- React Native Metro v0.71.3
|
||||||
|
- React 18.0.15
|
||||||
|
- `eslint-plugin-jsx-a11y` v6.6.1
|
||||||
|
|
||||||
|
For an exhaustive list check our release changelog on GitHub: [https://github.com/nrwl/nx/releases/tag/14.5.0](https://github.com/nrwl/nx/releases/tag/14.5.0)
|
||||||
|
|
||||||
|
## How to Update Nx
|
||||||
|
|
||||||
|
Updating Nx is done with the following command, and will update your Nx workspace dependencies and code to the latest version:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx migrate latest
|
||||||
|
```
|
||||||
|
|
||||||
|
After updating your dependencies, run any necessary migrations.
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx migrate --run-migrations
|
||||||
|
```
|
||||||
|
|
||||||
|
## Learn more
|
||||||
|
|
||||||
|
- 🧠 [Nx Docs](/getting-started/intro)
|
||||||
|
- 👩💻 [Nx GitHub](https://github.com/nrwl/nx)
|
||||||
|
- 💬 [Nx Official Discord Server](https://go.nx.dev/community)
|
||||||
|
- 📹 [Nrwl Youtube Channel](https://www.youtube.com/nrwl_io)
|
||||||
|
- 🥚 [Free Egghead course](https://egghead.io/courses/scale-react-development-with-nx-4038)
|
||||||
261
docs/blog/2022-10-14-whats-new-in-nx-15.md
Normal file
@ -0,0 +1,261 @@
|
|||||||
|
---
|
||||||
|
title: 'What’s new in Nx 15?'
|
||||||
|
slug: 'whats-new-in-nx-15'
|
||||||
|
authors: ['Juri Strumpflohner']
|
||||||
|
cover_image: '/blog/images/2022-10-14/ReZPz_brTiYN84yvR7Hi2w.png'
|
||||||
|
tags: [nx, release]
|
||||||
|
description: 'Nx v15 is finally here! Let’s go through all the great features that went into this major release.'
|
||||||
|
---
|
||||||
|
|
||||||
|
Nx v15 is finally here! Let’s go through all the great features that went into this major release.
|
||||||
|
|
||||||
|
{% toc /%}
|
||||||
|
|
||||||
|
## Growing fast!
|
||||||
|
|
||||||
|
Nx is currently at **~2.7 million NPM downloads per week**, which is incredible given we just crossed the 1 million downloads/week at the beginning of this year.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
Expect it to see growing much faster even in the coming months.
|
||||||
|
|
||||||
|
## Performance — Core, Nx Daemon
|
||||||
|
|
||||||
|
Performance optimizations are a recurring theme for us. We’re continuously optimizing Nx to make it even faster than it is now.
|
||||||
|
|
||||||
|
For example, when a cache hit needs to restore artifacts to some “dist” folder, we don’t touch the file system if it is not needed (because FS operations are costly). As a result, this would also not mess with any “watch” process on your dist folder, which you might use. And obviously, we detect whenever a file is missing. If you delete a single file from your “dist” folder, Nx will know and restore it properly.
|
||||||
|
|
||||||
|
This is possible because we offload some of the computation to a daemon process. This runs in the background to compute heavy operations like ensuring the project graph is always in sync, watching cache output locations and more.
|
||||||
|
|
||||||
|
You can read more about it here: [/concepts/nx-daemon](/concepts/nx-daemon)
|
||||||
|
|
||||||
|
## Package-based and Integrated Style Monorepos
|
||||||
|
|
||||||
|
In our 5 years of working with small and huge monorepos we’ve seen various setups. We’ve narrowed them down to two approaches:
|
||||||
|
|
||||||
|
- **package-based monorepos** — a collection of packages where each package within the monorepo is treated as a fully independent package. Meaning they have their own `package.json` with dependencies declared. To share and link packages locally within the monorepo, the "workspaces" feature from NPM/Yarn/PNPM can be used. Tools for this style are Nx, Lerna, Lage and Turbo.
|
||||||
|
- **integrated monorepos** — is usually a pre-configured and managed setup. You don’t have to rely on NPM/Yarn/PNPM workspaces for local linking and tooling helps with the low-level tooling setup and integrating various tools. Tools for this style are Nx and Bazel.
|
||||||
|
|
||||||
|
We improved and optimized Nx to be the best solution for both approaches. As part of this optimization, starting with Nx v15, when you run
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx create-nx-workspace
|
||||||
|
```
|
||||||
|
|
||||||
|
...you will now get a new question about whether you want to create a package-based monorepo or integrated style monorepo.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
There will be more content around choosing which style and even how to mix the two. Go with what works best for you and your current situation, and Nx will be there to handle the rest.
|
||||||
|
|
||||||
|
We also updated our docs to have two super short tutorials that illustrate the two approaches:
|
||||||
|
|
||||||
|
- [/getting-started/tutorials/typescript-packages-tutorial](/getting-started/tutorials/typescript-packages-tutorial)
|
||||||
|
- [/getting-started/tutorials/react-monorepo-tutorial](/getting-started/tutorials/react-monorepo-tutorial)
|
||||||
|
|
||||||
|
You can also read more about the concept here: [/deprecated/integrated-vs-package-based](/deprecated/integrated-vs-package-based)
|
||||||
|
|
||||||
|
## New Compact Syntax for Task Pipelines
|
||||||
|
|
||||||
|
Monorepos typically do not just have dependencies among projects but also among tasks. Let’s say you have a Remix app that depends on some `shared-ui` React-based library. Whenever you build or serve your app, `shared-ui` gets built before. This is required - especially in a package-based monorepo - because connected packages depend on the build artifacts, that is the compiled JS files.
|
||||||
|
|
||||||
|
You can define such a relationship easily in the `nx.json` by specifying the `targetDefaults` property. Nx had this for a while, but as part of some v14 minor version, we made it more concise.
|
||||||
|
|
||||||
|
Here’s an example:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
"targetDefaults": {
|
||||||
|
// run the build of all dependent packages first
|
||||||
|
"build": {
|
||||||
|
"dependsOn": ["^build"]
|
||||||
|
},
|
||||||
|
"dev": {
|
||||||
|
"dependsOn": ["^build"]
|
||||||
|
},
|
||||||
|
// run a package's build task before running publish
|
||||||
|
"publish": {
|
||||||
|
"dependsOn": ["build"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
You can read more here: [/concepts/task-pipeline-configuration](/concepts/task-pipeline-configuration)
|
||||||
|
|
||||||
|
## Fine-tune Caching with Inputs
|
||||||
|
|
||||||
|
Nx’s caching is already powerful, but you can get even more out of it by fine-tuning it to your workspace’s needs. This is done by defining `inputs` in `nx.json` for the various targets.
|
||||||
|
|
||||||
|
Here, for instance, we define that the `build` target should include all the files of a given project but not include test-related files. As a result, changing a Jest spec won't invalidate your `build` target cache.
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
...
|
||||||
|
"inputs": [
|
||||||
|
"{projectRoot}/**/*",
|
||||||
|
"!{projectRoot}/**/?(*.)+(spec|test).[jt]s?(x)?(.snap)"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Since these inputs are often re-used across different targets, they can be defined in a dedicated `namedInputs` property (think like a variable declaration) and re-used in the `targetDefaults`.
|
||||||
|
|
||||||
|
Here’s an example of the defaults that a new Nx workspace comes with:
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"namedInputs": {
|
||||||
|
"default": ["{projectRoot}/**/*", "sharedGlobals"],
|
||||||
|
"production": [
|
||||||
|
"default",
|
||||||
|
"!{projectRoot}/.eslintrc.json",
|
||||||
|
"!{projectRoot}/**/?(*.)+(spec|test).[jt]s?(x)?(.snap)",
|
||||||
|
"!{projectRoot}/tsconfig.spec.json",
|
||||||
|
"!{projectRoot}/jest.config.[jt]s"
|
||||||
|
],
|
||||||
|
"sharedGlobals": []
|
||||||
|
},
|
||||||
|
"targetDefaults": {
|
||||||
|
"build": {
|
||||||
|
"dependsOn": ["^build"],
|
||||||
|
"inputs": ["production", "^production"]
|
||||||
|
},
|
||||||
|
"lint": {
|
||||||
|
"inputs": ["default", "{workspaceRoot}/.eslintrc.json"]
|
||||||
|
},
|
||||||
|
"test": {
|
||||||
|
"inputs": [
|
||||||
|
"default",
|
||||||
|
"^production",
|
||||||
|
"{workspaceRoot}/jest.preset.js"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
You can read more here: [/recipes/running-tasks/configure-inputs](/recipes/running-tasks/configure-inputs)
|
||||||
|
|
||||||
|
## Nx Console
|
||||||
|
|
||||||
|
Nx Console has evolved to be a key part of Nx’s mission to improve the life of developers when working with Nx (and now also Lerna) monorepos. There have been tremendous improvements over the last couple of months. Here are some highlights!
|
||||||
|
|
||||||
|
The famous, so much loved [Nx Graph](/features/explore-graph) can now also be visualized within VSCode directly:
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
Get a more in-depth walkthrough here:
|
||||||
|
|
||||||
|
{% youtube src="https://youtu.be/ZST_rmhzRXI" /%}
|
||||||
|
|
||||||
|
There’s also a language server that comes with Nx Console now, which gives you intelligent autocompletion support in your configuration files:
|
||||||
|
|
||||||
|
{% tweet url="https://twitter.com/NxDevTools/status/1573323012476051456" /%}
|
||||||
|
|
||||||
|
## Website Redesign & Docs Updates
|
||||||
|
|
||||||
|
Every now and then, it’s time to revamp our website. Because it doesn’t feel as fresh as it did when you originally created it. So here we go! We created a new, condensed entry page with the most relevant information,
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
…followed by “tab-like” navigation
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
We keep improving our docs, and we invest a lot of time to make things easier for you all.
|
||||||
|
|
||||||
|
{% tweet url="https://twitter.com/victorsavkin/status/1580283233916186624" /%}
|
||||||
|
|
||||||
|
It is an ongoing process, and we have a lot of content to cover! We follow the [Diataxis](https://diataxis.fr/) framework for structuring our technical content where we want to clearly assign responsibilities to each page content, so it’s easy for you to get out of it what you most need. It is mostly structured around whether
|
||||||
|
|
||||||
|
- you want to get a deeper understanding of core concepts (“Concepts” section)
|
||||||
|
- you want to learn something new (“Tutorial” section) or
|
||||||
|
- you want a solution to a specific problem (“Recipes” section).
|
||||||
|
|
||||||
|
Besides the two new [package-based](/getting-started/tutorials/typescript-packages-tutorial) and [integrated style tutorials](/getting-started/tutorials/react-monorepo-tutorial) we also have two brand new reworked tutorials
|
||||||
|
|
||||||
|
- [/getting-started/tutorials/react-standalone-tutorial](/getting-started/tutorials/react-standalone-tutorial)
|
||||||
|
- [/getting-started/tutorials](/getting-started/tutorials)
|
||||||
|
|
||||||
|
Stay tuned for more updates to come.
|
||||||
|
|
||||||
|
## Cleanup for pure JS/TS packages and ESBuild support!
|
||||||
|
|
||||||
|
We streamlined our JavaScript / TypeScript packages to have dedicated ones for our bundlers:
|
||||||
|
|
||||||
|
- `@nrwl/webpack`
|
||||||
|
- `@nrwl/rollup`
|
||||||
|
- `@nrwl/esbuild` (NEW!)
|
||||||
|
|
||||||
|
So you can now generate a new JavaScript / TypeScript based package using the `@nrwl/js:lib` generator, which now allows you to choose between various builders:
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
And for those wondering. Yeah, [Vite](https://vitejs.dev/) is coming.
|
||||||
|
|
||||||
|
## Cypress v10 and Component Testing
|
||||||
|
|
||||||
|
Cypress has been an integral part of an Nx workspace for a long time. A couple of months ago, they shipped one of their biggest updates: Cypress v10. We’ve been working closely with the team to coordinate the integration into Nx and ensure it is as smooth as possible.
|
||||||
|
|
||||||
|
You can run the following command to migrate your existing Cypress to the latest version.
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx g @nrwl/cypress:migrate-to-cypress-10
|
||||||
|
```
|
||||||
|
|
||||||
|
Cypress v10 also comes with [Component Testing](https://docs.cypress.io/guides/component-testing/writing-your-first-component-test) (for React and Angular), and we provide generators for that to help you get started. You can add component testing to an existing project with
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx g @nrwl/react:cypress-component-configuration --project=your-projectnpx nx g @nrwl/angular:cypress-component-configuration --project=your-project
|
||||||
|
```
|
||||||
|
|
||||||
|
Read more here: [/recipes/cypress/cypress-component-testing](/recipes/cypress/cypress-component-testing)
|
||||||
|
|
||||||
|
## Angular: Improved Angular CLI Migrations and Standalone Components
|
||||||
|
|
||||||
|
We landed generators to support Angular developers in leveraging the new standalone components API in their Nx-based projects. Here’s a preview:
|
||||||
|
|
||||||
|
{% tweet url="https://twitter.com/NxDevTools/status/1567513106380894215" /%}
|
||||||
|
|
||||||
|
In addition, we improved the migration support for moving projects from the Angular CLI to an Nx workspace. Whether for a single Angular CLI project or to consolidate multiple Angular CLI projects into a single Nx workspace. Please read all about it here: [/recipes/angular/migration/angular](/recipes/angular/migration/angular)
|
||||||
|
|
||||||
|
## Easily add Nx to an existing repository
|
||||||
|
|
||||||
|
You can easily add Nx to an existing repository. This can be done manually by adding the `nx` NPM package or by running the following command:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx@latest init
|
||||||
|
```
|
||||||
|
|
||||||
|
It is as easy as it looks. The command analyzes the current workspace and then asks you a couple of questions to set up your workspace (including cacheable operations and configuring a task pipeline).
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
## How to Update Nx
|
||||||
|
|
||||||
|
Updating Nx is done with the following command and will update your Nx workspace dependencies and code to the latest version:
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx migrate latest
|
||||||
|
```
|
||||||
|
|
||||||
|
After updating your dependencies, run any necessary migrations.
|
||||||
|
|
||||||
|
```shell
|
||||||
|
npx nx migrate --run-migrations
|
||||||
|
```
|
||||||
|
|
||||||
|
## Learn more
|
||||||
|
|
||||||
|
- 🧠 [Nx Docs](/getting-started/intro)
|
||||||
|
- 👩💻 [Nx GitHub](https://github.com/nrwl/nx)
|
||||||
|
- 💬 [Nx Official Discord Server](https://go.nx.dev/community)
|
||||||
|
- 📹 [Nrwl Youtube Channel](https://www.youtube.com/nrwl_io)
|
||||||
|
- 🥚 [Free Egghead course](https://egghead.io/courses/scale-react-development-with-nx-4038)
|
||||||
BIN
docs/blog/images/2021-06-15/92NTlO7eM7-mc9WD.avif
Normal file
|
After Width: | Height: | Size: 29 KiB |
BIN
docs/blog/images/2021-06-15/PmhVG4DF-OKtbl.avif
Normal file
|
After Width: | Height: | Size: 20 KiB |
BIN
docs/blog/images/2021-06-15/XISTgZIBj5ZZ3Sp7.avif
Normal file
|
After Width: | Height: | Size: 12 KiB |
BIN
docs/blog/images/2021-06-15/jFVfKEglfQIM9QsP.avif
Normal file
|
After Width: | Height: | Size: 8.8 KiB |
BIN
docs/blog/images/2021-06-15/jFVfKEglfQIM9QsP.png
Normal file
|
After Width: | Height: | Size: 145 KiB |
BIN
docs/blog/images/2021-06-15/lS7eewNQuZzQ72kU.avif
Normal file
|
After Width: | Height: | Size: 2.7 KiB |
BIN
docs/blog/images/2022-06-09/mbcZT24F7G8mbRGEnJ7iEg.avif
Normal file
|
After Width: | Height: | Size: 42 KiB |
BIN
docs/blog/images/2022-06-09/uScdSDGP4NgCKFrPdznbhw.avif
Normal file
|
After Width: | Height: | Size: 6.4 KiB |
BIN
docs/blog/images/2022-06-09/uScdSDGP4NgCKFrPdznbhw.png
Normal file
|
After Width: | Height: | Size: 90 KiB |
BIN
docs/blog/images/2022-07-05/lpmHhIiE9v5yJI6nLi2dlw.avif
Normal file
|
After Width: | Height: | Size: 6.1 KiB |
BIN
docs/blog/images/2022-07-05/lpmHhIiE9v5yJI6nLi2dlw.png
Normal file
|
After Width: | Height: | Size: 87 KiB |
BIN
docs/blog/images/2022-08-02/H1XArfg-tCgD0ZUp.avif
Normal file
|
After Width: | Height: | Size: 28 KiB |
BIN
docs/blog/images/2022-08-02/IWGJcienK4L_oGxl.avif
Normal file
|
After Width: | Height: | Size: 11 KiB |
BIN
docs/blog/images/2022-08-02/ZUzLD-4JgrEBIZb3dXOvag.avif
Normal file
|
After Width: | Height: | Size: 6.3 KiB |
BIN
docs/blog/images/2022-08-02/ZUzLD-4JgrEBIZb3dXOvag.png
Normal file
|
After Width: | Height: | Size: 90 KiB |
BIN
docs/blog/images/2022-08-02/dhbe8hFyjEm_K86A.avif
Normal file
|
After Width: | Height: | Size: 24 KiB |
BIN
docs/blog/images/2022-10-14/92hOex9StyREA608.avif
Normal file
|
After Width: | Height: | Size: 22 KiB |
BIN
docs/blog/images/2022-10-14/CImYERzLu-0nlydk.avif
Normal file
|
After Width: | Height: | Size: 10 KiB |
BIN
docs/blog/images/2022-10-14/P5_ddaNI5vSWA9Vz.avif
Normal file
|
After Width: | Height: | Size: 24 KiB |
BIN
docs/blog/images/2022-10-14/ReZPz_brTiYN84yvR7Hi2w.avif
Normal file
|
After Width: | Height: | Size: 53 KiB |
BIN
docs/blog/images/2022-10-14/ReZPz_brTiYN84yvR7Hi2w.png
Normal file
|
After Width: | Height: | Size: 740 KiB |
BIN
docs/blog/images/2022-10-14/SfKdIa3JKTG7F-tg.avif
Normal file
|
After Width: | Height: | Size: 7.3 KiB |
BIN
docs/blog/images/2022-10-14/imK9iVBVxn1-Vppk.avif
Normal file
|
After Width: | Height: | Size: 16 KiB |
BIN
docs/blog/images/2022-10-14/s2FGPP87Y9HbZlTP.avif
Normal file
|
After Width: | Height: | Size: 26 KiB |
BIN
docs/blog/images/2022-10-14/ti_BMWvFm9t9RVqI.avif
Normal file
|
After Width: | Height: | Size: 29 KiB |
@ -1,6 +1,6 @@
|
|||||||
# Nx 14.5
|
# Nx 14.5
|
||||||
|
|
||||||
[Read the 14.5 release blog post](https://blog.nrwl.io/nx-14-5-cypess-v10-output-globs-linter-perf-react-tailwind-support-c15f0b5dc2fc)
|
[Read the 14.5 release blog post](/blog/nx-14-5-cypress-v10-output-globs-linter-perf-react-tailwind-support)
|
||||||
|
|
||||||
Here are some of our feature highlights:
|
Here are some of our feature highlights:
|
||||||
|
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
# Nx 15.0
|
# Nx 15.0
|
||||||
|
|
||||||
[Read the 15.0 release blog post](https://blog.nrwl.io/whats-new-in-nx-15-7e14e1ff282d)
|
[Read the 15.0 release blog post](/blog/whats-new-in-nx-15)
|
||||||
|
|
||||||
Here are some of our feature highlights:
|
Here are some of our feature highlights:
|
||||||
|
|
||||||
|
|||||||
@ -62,4 +62,4 @@ Read more about the proper usage of this rule:
|
|||||||
- [Tag in Multiple Dimensions](/recipes/enforce-module-boundaries/tag-multiple-dimensions)
|
- [Tag in Multiple Dimensions](/recipes/enforce-module-boundaries/tag-multiple-dimensions)
|
||||||
- [Ban External Imports](/recipes/enforce-module-boundaries/ban-external-imports)
|
- [Ban External Imports](/recipes/enforce-module-boundaries/ban-external-imports)
|
||||||
- [Tags Allow List](/recipes/enforce-module-boundaries/tags-allow-list)
|
- [Tags Allow List](/recipes/enforce-module-boundaries/tags-allow-list)
|
||||||
- [Taming Code Organization with Module Boundaries in Nx](https://blog.nrwl.io/mastering-the-project-boundaries-in-nx-f095852f5bf4)
|
- [Taming Code Organization with Module Boundaries in Nx](/blog/mastering-the-project-boundaries-in-nx)
|
||||||
|
|||||||
@ -187,7 +187,7 @@ work happens. The rest is either left as is or restored from the cache.
|
|||||||
|
|
||||||
## Distributed task execution
|
## Distributed task execution
|
||||||
|
|
||||||
Nx supports running commands across multiple machines. You can either set it up by hand or use Nx Cloud. [Read the comparison of the two approaches.](https://blog.nrwl.io/distributing-ci-binning-and-distributed-task-execution-632fe31a8953?source=friends_link&sk=5120b7ff982730854ed22becfe7a640a)
|
Nx supports running commands across multiple machines. You can either set it up by hand or use Nx Cloud. [Read the comparison of the two approaches.](/blog/distributing-ci-binning-and-distributed-task-execution)
|
||||||
|
|
||||||
When using the distributed task execution, Nx is able to run any task graph on many agents instead of locally.
|
When using the distributed task execution, Nx is able to run any task graph on many agents instead of locally.
|
||||||
|
|
||||||
|
|||||||
@ -81,7 +81,7 @@ A crucial feature in Nx is the ability to not only parallelize your tasks on a s
|
|||||||
- **Distributed task execution has a significantly higher impact on the ability to scale the repo than the computation cache.** You can scale without the cache, you cannot scale without the distribution.
|
- **Distributed task execution has a significantly higher impact on the ability to scale the repo than the computation cache.** You can scale without the cache, you cannot scale without the distribution.
|
||||||
- This is the biggest feature related to performance and scaling that Turborepo is missing. And it’s by far the hardest one to build.
|
- This is the biggest feature related to performance and scaling that Turborepo is missing. And it’s by far the hardest one to build.
|
||||||
|
|
||||||
If you want to learn more, check out our article on [Distributing CI - Binning and Distributed Task Execution](https://blog.nrwl.io/distributing-ci-binning-and-distributed-task-execution-632fe31a8953)
|
If you want to learn more, check out our article on [Distributing CI - Binning and Distributed Task Execution](/blog/distributing-ci-binning-and-distributed-task-execution)
|
||||||
|
|
||||||
#### 9. Editor support
|
#### 9. Editor support
|
||||||
|
|
||||||
|
|||||||
@ -62,4 +62,4 @@ Read more about the proper usage of this rule:
|
|||||||
- [Tag in Multiple Dimensions](/recipes/enforce-module-boundaries/tag-multiple-dimensions)
|
- [Tag in Multiple Dimensions](/recipes/enforce-module-boundaries/tag-multiple-dimensions)
|
||||||
- [Ban External Imports](/recipes/enforce-module-boundaries/ban-external-imports)
|
- [Ban External Imports](/recipes/enforce-module-boundaries/ban-external-imports)
|
||||||
- [Tags Allow List](/recipes/enforce-module-boundaries/tags-allow-list)
|
- [Tags Allow List](/recipes/enforce-module-boundaries/tags-allow-list)
|
||||||
- [Taming Code Organization with Module Boundaries in Nx](https://blog.nrwl.io/mastering-the-project-boundaries-in-nx-f095852f5bf4)
|
- [Taming Code Organization with Module Boundaries in Nx](/blog/mastering-the-project-boundaries-in-nx)
|
||||||
|
|||||||
@ -165,4 +165,4 @@ Matching just a single source tag is sometimes not enough for solving complex re
|
|||||||
|
|
||||||
## Further reading
|
## Further reading
|
||||||
|
|
||||||
- [Article: Taming Code Organization with Module Boundaries in Nx](https://blog.nrwl.io/mastering-the-project-boundaries-in-nx-f095852f5bf4)
|
- [Article: Taming Code Organization with Module Boundaries in Nx](/blog/mastering-the-project-boundaries-in-nx)
|
||||||
|
|||||||