How do I keep yarn workspaces dependencies in sync - yarnpkg

Let's say I have multiple packages in my yarn workspaces.
#mycompany/utils
#mycompany/app
#mycompany/serv
Let's say each of these packages has a dependency on lodash. I want to make sure that they all have the same lodash version.
Is there a way to do that in each of the package.json?

Use syncpack to force all sub-packages in a monorepo uses the same version of each dependency.
Install in the root package.json:
yarn add --dev -W syncpack
Run (Recommnded: Run on every commit using husky):
syncpack list-mismatches
More info: https://github.com/JamieMason/syncpack

Related

Yarn & Monorepo: Prevent using local packages

I have a yarn/lerna monorepo with multiple packages that depend on each other. If I add packageA as a dependency to packageB and execute yarn install I see that node_modules/packageA is actually a symlink to packages/packageA instead of the published version of that package.
This creates problems on CI if packageB is build before packageA - the build fails because node_modules/packageA just points to the bare sources, without the build products (because packageA has not yet been built).
How can I force yarn to always download the published version of packageA?
yarn --version: 1.22.10
sidenote: If I wanted to use a local version of packageA instead, I would use yarn link or a local path instead of a version in package.json. Why is yarn defaulting to this behaviour?
One options is: "focussed workspaces" - see the guide here.
In my case, I added a file packages/packageB/.yarnrc that specifies to always use the --focus argument for yarn install:
--install.focus true
This will make sure that packageB has a copy of the published packageA in it's own node_modules folder.
However: This only works for one package at a time.
You can just build packages in order of dependencies. So in your case it'd be something like this in your CI (assuming there is a script entry called "build" in package.json of the packages):
yarn workspace packageA run build
yarn workspace packageB run build
This way you control the order of builds,they complete successfully, and you don't have to force using published package.

How does yarn workspaces treat external dependencies with different versions?

Let's say a I have the following monorepo structure using Yarn workspaces:
node_modules
packages
admin-app // WEB APP FOR ADMIN DASHBOARD
user-app // PUBLIC WEB APP FOR REGULAR USERS
packages.json
Let's say both admin-app and user-app will need to install React as a dependency.
Here is what I'll do to add React on both workspaces:
yarn workspace admin-app add react
yarn workspace user-app add react
Currently, this results in both of my packages depending on "react": "^17.0.2".
Inside my root node_modules, I can see that there is only one react folder in it. And the version is, as expected, 17.0.2.
But what if at some point I update React on admin-app and maybe forget to update it on the user-app. How will yarn install those two different versions of React? For example: 17.0.5 and 17.0.2?
As a I writing this question I've decided to test it.
Here is what I did:
yarn workspace user-app add react // THIS WILL INSTALL THE LATEST 17.0.2
yarn workspace admin-app add react#17.0.1
This was the result:
node_modules
react v17.0.1
packages
admin-app
user-app
node_modules
react v17.0.2
Yarn chose to keep the older version 17.0.1 in the root node_modules folder, and it installed the 17.0.2 in the user-app/node_modules folder.

Install a dependency and save to package.json for a sub-package in yarn workspaces

I am trying to use Yarn Workspaces for my app that I am splitting into multiple packages such that I can share code between the mobile and web version of the app. Let me explain what I am trying to do with an example.
Let's say I currently have a mobile app called awesome-app. I am refactoring it by taking out the shared code and creating three packages as follows:
awesome-web
awesome-mobile
awesome-shared
Let's say I want to add new functionality to awesome-mobile for which I have to install depA to awesome-mobile. How can I do that such that yarn only installs depA and updates the package.json for the awesome-mobile. I tried using command yarn package <package-name> add depA but it ended up installing all the dependencies again which I want to avoid.
Also, let's say I want to use awesome-shared in awesome-web. Is there a yarn command such that it installs and updates the package.json for awesome-web automatically. Currently, I do it by hand and then I do yarn install in the root folder which ends up installing all the dependencies again.

Yarn How to Specify Install Path for a Package

I migrated from bower away and now my dev dependencies are in node_modules/ while my prod dependencies are in node_modules/#bower_components/. This is good because I can easily grab all the front end dependencies in gulp with node_modules/#bower_components/**/*. Now I want to install new "bower" packages and I also want them appear in node_modules/#bower_components/ but they are installed into node_modules/. I tried to use yarn add <package> --modules-folder node_modules/#bower_components but this moves all my packages into the subfolder.

How to run go command using only vendor dependencies?

I keep running into the issue where I install dependencies locally, it works fine, I push to continuous integration server, and then it breaks because I forgot to godep save ./... the dependency.
How can I run the go command but require vendor imports?
Edit:
I'm using go1.6. I want the command to fail if a 3rd-party dependency does not resolve to vendor. In other words, is there a way to stop resolving dependencies in $GOPATH during tests?
I can't change the environment variable because then none of my project modules can be resolved. How can I force vendor dependencies?
There is no way to prevent builder to scan $GOPATH for packages. It seems, that you use not really good flow for manage dependencies. I recommend you to use glide for a vendoring.
Most recommended workflow:
Keep actual list of dependencies in glide.yaml.
Run glide up after any changes in glide.yaml. It will install all dependencies to vendor directory and generate glide.lock with fixed package versions. Commit glide.lock to VCS. Do not change manually glide.lock.
Do not commit vendor directory to VCS.
Run glide install on your CI or build server to install dependencies by glide.lock to vendor.
Build.
A migration from godep to glide may be done easily, because glide has a command to migrate Godeps.json to glide.yaml.

Resources