Workspaces

Setting up npm workspaces in our mono-repo

Project Source Code

Get the project source code below, and follow along with the lesson material.

Download Project Source Code

To set up the project on your local machine, please follow the directions provided in the README.md file. If you run into any issues with running the project source code, then feel free to reach out to the author in the course's Discord channel.

  • |

Lesson Transcript

  • [00:00 - 00:12] So, we're going to be using something called workspaces. That was introduced by a package manager called Yarn a while ago, but it is now supported by all the major package managers.

  • [00:13 - 00:28] I'm going to be using NPM in this course because it's the standard, and I think it works very well. But you're free to use any of the others, PNPM or Yarn or whatever you want, because I think all of them support all of this that we're going to be using in this course.

  • [00:29 - 00:41] There are tools for managing mono repos when your project grows larger that you might want to look into, such as Lorna or Turbo repo. Those two both use workspaces internally, but they offer some additional features.

  • [00:42 - 00:54] So they might come in handy at a later point, but for all that we will need it for right now, we will be using just workspaces and that will work just fine. So let's get started.

  • [00:55 - 01:03] I have a completely clean this code session here. There is nothing in this folder.

  • [01:04 - 01:08] I just created the folder called easy booking, and we will start working in that. So I will start.

  • [01:09 - 01:22] It hasn't even been initialized to forget. So let's just initialize a git repository, and then we will say NPM init for initializing a package JSON in the root.

  • [01:23 - 01:41] It will ask us some questions, and we will change this to easy booking - mono repo just to keep track of or make sure that we remember that this is the mono repo package JSON. It's not really something that is a package in and of itself.

  • [01:42 - 01:52] The rest of these questions aren't really interesting. We can set the license to unlicensed just because this is not going to be something we will be publishing.

  • [01:53 - 02:05] We now have a package JSON here in our folder, which contains these things. I will add one thing to this, which is private.

  • [02:06 - 02:22] And the reason for that is that it's - at least it was in Yarn, I'm not sure if NPM requires it, but it used to be at least a requirement. And it is to make sure that you don't accidentally publish your mono repo to the NPM registry, which is certainly not something you want to do.

  • [02:23 - 02:44] Now there's sort of a tradition of having a folder called packages in your mono repo where you will put all your packages in. I personally like to also have something called app or apps or services, which is where I put in the particular packages that will sort of spin up.

  • [02:45 - 03:00] So packages itself will just contain shared libraries and then services will contain the things that I actually deploy somewhere. So let's create two folders out here in the root.

  • [03:01 - 03:06] Packages and services. Did I spell that right?

  • [03:07 - 03:13] I did. There we will put our stuff into those two folders.

  • [03:14 - 03:20] The architecture that we're creating here is really quite simple. We're going to have two services, a back end and a front end.

  • [03:21 - 03:31] You can argue that the front end isn't really a service, it's a bundle, but for this course we're going to talk about it as a service. And then we're going to have one shared package called schema.

  • [03:32 - 03:44] The schema will take care of database migrations, but it will also be where we supply our TypeScript types, both to the back end and to the front end. So that is where Kennel will be generating the types.

  • [03:45 - 03:57] Let's start by creating the schema package. So I go into the packages folder here and I create a schema folder.

  • [03:58 - 04:12] And in that I will run npm in it again. And you can see that Fish Shell is squealing on me, that I've done this before, but what we're doing here basically is we will be using the scope parameter to npm in it .

  • [04:13 - 04:26] So basically we're going to tell them that we're going to be creating this schema package in the easy booking scope. And all that really does is you can see it suggests this name and that is what the scope means.

  • [04:27 - 04:40] So this is now schema in the easy booking scope and we're going to accept all of these things that it suggests for us because we don't really care much about any of this. So now we have the schema package.

  • [04:41 - 04:47] Let's go and do the same thing for the back end package. So that is in services.

  • [04:48 - 04:58] We'll create a back end folder and we will run npm in it and we will use the scope parameter again. So we do this.

  • [04:59 - 05:13] And we just accept everything it suggests for us. And we now have a package JSON file in schema and we have an almost identical one in back end.

  • [05:14 - 05:20] Nice. So in order to use these in the workspace, we need to add them to our package JSON out in the root.

  • [05:21 - 05:31] And the way we do that is by creating a workspace's entry here. And that takes an array of things.

  • [05:32 - 05:46] And you can see that the copilot here is suggesting that I add packages slash asterisk, which is quite a common way of doing this when you create a monorepos. But I don't particularly care for it.

  • [05:47 - 06:02] The reason is that when you do this, you don't specify the order of things. And since we're not using learner or turbo repo or anything that handles that sort of thing for us, we can do very, very basic dependency management by just specifying the order of packages out here.

  • [06:03 - 06:21] And we want to make sure that whenever we build our back end, the schema has been built first. So we're going to add packages slash schema before services slash back end.

  • [06:22 - 06:23] And add a comma there. So everybody's happy.

  • [06:24 - 06:40] I don't think there's much of a hassle to have to add all the things that you want in your workspace is to package JSON that adds a little bit of plumbing, but it's definitely something you can live with. And this way it's explicit, which I just find is nice in every way.

  • [06:41 - 06:43] So this way we will have the dependency specified.