Check out a free preview of the full Introduction to Node.js, v3 course:
The "Custom CLI Setup" Lesson is part of the full, Introduction to Node.js, v3 course featured in this preview video. Here's what you'd learn in this lesson:

Scott explains command-line interfaces, demonstrates creating a Node.js project using npm, and covers the contents of the generated package.json file. The segment also includes linking to the file and defining the script's environment with a hashbang.

Get Unlimited Access Now

Transcript from the "Custom CLI Setup" Lesson

[00:00:00]
>> Okay, so what is a CLI then? Well like I said, you've been using a CLI this whole time. Basically, a CLI is just an app that runs in your terminal that's basically it. It's short for command line interface because this is a command line and this is how you the best way I can think about a CLI always think about is like it's it's you chatting to your computer.

[00:00:22] That's the best way I can describe it. The only problem is you can't do it in human language. You can only do it with like these commands, so you have to know the commands and those commands execute code. Now some commands are built in like ls, right? mkdir, depending on what platform you're on.

[00:00:39] These commands are built in. These are also CLIs other commands you can make yourself or you can download. Today we're gonna make our own CLI that we can name whatever we want. We'll be able to use it from here, just like we can use ls, right? That's basically what a CLI is.

[00:00:56] So I listed some of the common ones you might see like ls, rm to remove things, cd to change command, mkdir, different things like that. But like I said, we're gonna make our own custom one and it's actually really not that hard to make one. So it just depends on how sophisticated it is, but it's really not too complicated.

[00:01:19] Also have some examples here of just like how you can install some of those CLIs. The thing to note here is that a CLI, it doesn't matter what language you build a CLI in any language that can run on your computer, you can make a CLI in, not just Node.js.

[00:01:36] Like you can make one in Bash if you want to and it doesn't matter. You can so and also when you run that CLI, it doesn't really matter what language it was built in as long as your operating system has that runtime, that environment, it can execute that CLI as well.

[00:01:53] In fact, some of the CLIs you probably have on your computer probably were not even made with Node or JavaScript or made with something else but yet you still executing them. So it's just a very, it's probably the most flexible type of app that is out there because it runs on operating system.

[00:02:08] You can make it with any single language and it has access to your home machine, which means it can do anything. So take that apply to some remote machine in the cloud that's got like crazy amount of compute GPUs, CPUs and imagine being able to do anything. It's a powerful application, it's more than just making files and removing them.

[00:02:26] You can do some pretty crazy stuff with CLIs. So that's basically what a CLI is. It's a way to chat to your computer, it's an app in your terminal. Okay, well, let's get started making our CLI and yeah get the ball rolling with that. So first thing we want to do is we need to convert our folder that we made here where we tested our file into a Node.js project.

[00:02:50] The best way to do that is using this other CLI that you didn't know you had called npm. You didn't install npm, it comes installed with Node.js. If you install Node.js, which everyone here did you should have npm. So now you can run npm init, which stands for initialize.

[00:03:07] And it's just gonna give you this prompt. It's gonna ask you some questions, you can see it's actually gonna type some stuff in here. You can see what it says and fill this out if you want or you could just keep hitting Enter until it goes away. And it will go away you could avoid all that if you do npm init --yes.

[00:03:27] Which means say yes to everything. So I don't have to do it and it'll do the same thing. So basically what's happening here and then it'll give you this output. This output is basically this. It creates this new file called a package.json and it puts all this in it.

[00:03:46] Basically, when you put a package.json in your folder, your project. This allows you to take advantage of everything that Node.js has to offer as far as like modules, scripts, different things like that and it's not specific to Node.js. A lot of operating system languages have their own configuration file.

[00:04:09] In which you can configure things like dependencies and stuff like that. So this is just JavaScript or Node.js version of that is a package.json. So here we go we got a name, we got a version, we got the main file. Honestly, none of this stuff matters for the most part unless you're creating a package and once you deploy that you want other people to be able to download and you want to share that package.

[00:04:31] Well, we're making an app not a package. So we don't really care about a lot of this stuff. This really only matters for again, I'm creating a package that other people can use. So we don't have to really worry about that. But you get this, this is what you get when you do npm init.

[00:04:47] All right, so now that we have that what we want to do is in that index.js file that you may or may not have, just make sure you have it. Just make sure you have a log in here. I'm just gonna say, hello world, like that. And then now, that's our program that's our CLI.

[00:05:09] All it does is log we just need to make it a CLI. I want to be able to come into my terminal and type in some command and be able to run that file basically. So in order to do that, we need to go back into our package.json and we only got to add one field really, this 'bin' field.

[00:05:28] So if you go to your package.json and on the top level this object, if you just do bin, which is an object. And then the first key is just the name of the CLI that you want to make in this case I'm gonna make a CLI called note.

[00:05:48] And then I'm gonna point it to that index.js file. So what does this actually mean, this is just whenever you create. Actually, I'II just show it's best if I show you. So if type in which node you see somewhere in this path there's word called bin, right? You think I've bin just like this is where all your CLI live.

[00:06:13] Every CLI that you make is gonna live in a folder called bin in your computer. Why is it called bin? I don't know, that's what its called it's bin. So when we put that in our package.json, this is us saying we want to create a new entry in that bin folder called note and here's the code to execute when someone uses it.

[00:06:31] So you probably want a globally unique CLI name the worst thing you wanna do is like make a CLI called git because there is a CLI called git. And I don't know which one gonna run, which one they installed last I guess so you gonna kinda think about it and point to a file.

[00:06:50] So now that we have that the next thing we want to do is there is a couple of ways to test this locally. Obviously we could just run this file like we did before with Node but we want to run it with our note command or whatever you call it yours you don't have to call it note.

[00:07:05] We could install this like a package using npm but I think the best way to do is just do what's called a symlink so in your terminal if you're in the path to that repo you're on the route. So you should see index, you should see package. You can just type an npm link.

[00:07:23] Like okay, yeah see I do get the error already have one that exists. I need to overwrite mine. I was gonna say force that link. So what this is gonna do is just going to take our CLI and it's going to install it in that bin folder inside of our computer.

[00:07:44] So we're now able to use the note command. I got the error when I ran npm link because again, I already did this on the finished app that I have over here. So it's like, hey, you already got something called note it's already linked. Basically what link is doing is creating a symbolic link between our package here, our file here with our operating system file system.

[00:08:08] So it's not actually like installing it there but it's creating like a virtual reference to it. So when it tries to read that program they don't know the point of this file. And the reason we're doing this because it's just easier to develop. If we did the other way around where we installed it globally, every change we made, we have to reinstall it every single time.

[00:08:26] Whereas now because it's a symlink, it's always pointing to this. So we just hit save and it's done we don't have to keep reinstalling it. So it's better to develop what a symlink that it is installing it. Cool, so now I should be able to type in which note like this and I can see that.

[00:08:41] Yeah, I do have something called note installed on my computer somewhere because I just did that's a symlink there. So now I can just type in note and hit Enter and you should get this error, all right. Everybody gets to this point where they get this error? Yeah why is that I know if I run this code index.js like this it works so I know the file it's good JavaScript.

[00:09:13] I didn't write bad JavaScript, I know it works I just ran it just now. But for some reason when I ran it with my note command, it says, syntax error near unexpected. That's not a syntax error, that's just a console. Okay, there's a really good reason for this that's because we now installed a bin tool which is a CLI.

[00:09:37] Remember when I told you a CLI can be made in any single language in fact every language pretty much you can make a CLI. Okay, that's the problem our computer doesn't know what runtime to run this file. Then it's like okay cool, you made something but like is this Python?

[00:09:51] Is this C-Sharp, what is this? It doesn't know so I actually don't know what environment is trying to run it in right now. Probably just bash, but it's like, I don't get it. It's not gonna look at the file name and be like, yeah, this is JavaScript, cool.

[00:10:05] Or it's not gonna like read your code and interpreted as JavaScript and figure it out. You have to tell it and there's a way to do that so let's figure that out. You have to add something at the top of your file which is called a hashbang. And it's basically a comment that's ignored from the interpreter but it's meant for your operating system.

[00:10:29] It's meant for your computer, it's going to tell it what environment this file should be ran in. So in this case, we want to use this one or is this like this #!/user/bin/env node. So we have to add this to the top. You can't have any thing before it's not even a new line.

[00:10:50] You can't do that you can see it automatically breaks even when I do that. Like it just it literally has to be the first thing in the file. Because it's not it's not a traditional JavaScript comment. We know JavaScript comments look like this or they look like this.

[00:11:02] So it's not a it's not even a JavaScript comment. It's something that only the machine cares about. The JavaScript interpreter won't even see this. So now that we have that, we can hit Save, we can go back. Now I can type in note. I do get hello world because it knows that it's JavaScript.

[00:11:24] Yes.
>> So if we don't have Zsh installed or are we gonna it looks like I don't have that installed in mine.
>> Are you getting an error?
>> It says command not found.
>> So command not found means this that means your link didn't work so if you type in which note what does it say?

[00:11:47]
>> Yeah, says note not found.
>> Exactly so what you wanna make sure you do is you wanna make sure you run npm link.
>> Okay.
>> To link that CLI to your computer.
>> Okay, then if I type in which note?
>> Then if you type in which note, you should be able to see.

[00:12:07] All right, just to show you, if I change this to node not note and did that, it'll break. Like no, just there's literally no environment called node, that this is not a real path. All right, so it's reading this path and it's using that execution to do that so Cool, you just made your first CLI [LAUGH] easy, that's how easy it was.