 Hey, guys, I'll be talking about how life can be better with Git hooks. I'm Deepank. I'm an engineer at PayPal. So has anyone here used Git hooks? I'm sure everyone must have used Git, but Git hooks. A lot of us. Anyone not heard of Git hooks before? OK, still a lot. So advanced users, please bear with me. I'll be wanting to cater to all sorts of audiences. So what are Git hooks? Well, Git hooks are essentially just custom scripts that you can write and customize the internal behavior of Git. So on certain events of Git, you can write scripts that are triggered at certain points of time. So well, why use them? Because they make your life much better. So Git is a tool that we use almost every hour. Most of us are software engineers, I believe. So Git hooks can really be used to make life better. And the best part about it is that you can use any language to write them. So as long as the language is executable by the environment, you're good to go. So where are these Git hooks? So let's say if sample Git repo is our repo, and we go to the .git hidden directory edit, and list the files, there's a Git, there's a hooks directory. Basically, the hooks are located there. And there are basically two types of hooks, client hooks and server hooks. Client hooks are the hooks that you install on a developer machine. So they're for individual developers to enhance their programming environment and basically just make their development development workflow a bit easier. Whereas server hooks are hooks that are installed on remote Git repos. And they could be used for a variety of reasons, like sending notifications on pushes and things like enforcing some policies, like code quality and all. So if we look at what are the sorts of Git hooks present in your hooks directory, there are a number of Git hooks. There are nine in total by default. So in a newly initiated Git repo repository, all the Git hooks are extended with the .sample extension. So what that .sample does is it tells Git that this is not to be executed. So if you just remove the .sample from the extension, it'll execute the script. So you can see there are a number of hooks that can be used for a variety of reasons. Some important hooks that many of us use in the everyday life are for Git hooks that are in the commit workflow. So when you type Git commit, what happens is these Git hooks get executed in this order. So the pre-commit hook gets executed first. So basically before anything happens, when you type Git commit, the pre-commit hook is run. So what this is typically used for is things like running unit tests in your app, checking for code quality. Those who have done JavaScript might have heard about JSCS and things like that. So those things can be hooked into this to make sure that you're committing something that's correct and runs well. The prepare commit message is run when you typically, when you write Git commit, it opens an editor which allows you to edit the commit message. So it allows you to modify the commit message that comes up in that editor. After that one is run, the commit message hook is run. That is something when you save that file, it could be used to append something onto that file or really modify the actual message automatically. And then after that is the post commit which could be used for a number of reasons, not the most common one, but it could be used for things like notifying the user or doing something like that. So one thing to note about it is if you, in any of these three commit hooks, if you exit with a status which is non-zero, it's actually going to abort the Git commit. So that is something we use. So let's look at a simple, very, very simple example of a hook. So this is a pre-rebase hook. It's not part of the commit workflow, but it hooks onto the Git rebase command. So if we go to the pre-rebase hook and so basically I told that we could write hooks in any language. So this is an example in shell script. So what the first line does is just tell Git what language is this in as in the path for the interpreter. So this is just an example that it echoes a message and exits with status 1. So basically rebase is totally not allowed. Some people believe that rebase is dangerous. So this thing totally doesn't allow rebases. When we type Git rebase, a particular branch, this is going to abort rebase and the user is not allowed to rebase. So one thing to note is that client hooks should not particularly be used for enforcing stuff because it's a client hook. Any client can just, we can just go to the hooks directly and edit it. It's basically used for making things simpler for us. That's all it's for. But what can be used for enforcing stuff is something like server hooks. So server hooks are actually hooks that are in the server repose, the Git repose that you push your repo to. So some examples are pre-receive, update, and post-receive. So pre-receive is the hook that's run when the server just receives a Git push, for example. The update is when it updates its repo with the new commits that you've sent it. And post-receive is typically used for notifying or sending emails when the Git push is completed. And yeah, typical users are enforcing policies like code quality, avoiding console.logs, and things like that inside your code, and sending emails. And the catch here is GitHub doesn't allow server hooks. Is there a question? Sure, go ahead. Is this something we can use with Bitbucket and GitHub? No, that's what I was going to get into. The catch here is we cannot use this with GitHub. Bitbucket, I'm not sure. But GitHub, you definitely can't use it because the thing is, if you allow a user such access, he can really run any script on the server. So that's why they don't allow. What's recommended is to use web hooks and stuff like that to actually run another service, which runs in some events. And the client hooks, are they shared with other clones of the repository? No, it's not actually the .git repo. The .hooks is not shared when you get cloned. So what you could do is link. What's recommended typically to share the scripts is, so let's go back and see the .git repo here. It's not actually the hooks directory is not shared across when you clone a redirect directory. So some people say that these hooks are meant for individual developers. But some other people say that, well, we want to share these hooks. And across a team, for example. So what's a recommended approach is to have another directory inside your main repo, which is meant for hooks, where you store the hooks itself, the scripts. And you could document in your readme, things like that. When you clone, you sim link your scripts to that script. Yeah. Isn't there a money for a code texture? Sorry? Isn't there a money for a code structure? Because if you match from the remote that you check out a branch that is not, that has malicious intent, wouldn't you be accidentally running those scripts there? Do you copy the hooks files into the people that are here? Or do you sim link them? We can sim link them. We could copy as well. Depends. So if you sim link them, and you check out some new branch, which contains a malicious code, like rm-rf. Yeah. So that's always there, right? If you're working in a team, you need to make sure no one has that script. But that's definitely that can be done. What if you're flawless? Sorry? Yeah. Yeah, so. But yeah, that's a good point. There's always this thing of responsibility with hooks. With hooks, you can really run anything, because you have the access to run the script. OK, so that's about server hooks. And that's all I had. It's a very simple talk. Any other questions? Best client and server hooks? I actually use the pre-commit hook the most. So I work in Node.js. And well, I'm at PayPal, so Douglas Crockford, if you know about him, he's a big, because he wrote JS lint. He's a big seller of JS lint. So we hook JS lint into the pre-commit hook, and then run for code quality. And we also run unit tests with the pre-commit hook. Yeah. If you return a non-zero access from the pre-received hook, will it actually prevent push or happening? I believe so. I haven't tried that out, but I think so. Yes, you can stop a push if you return a non-zero access from the pre-received hook. In fact, in my project, they use that to make sure that the commit hook is on the format, and if it doesn't follow that format. Yeah, there are actually you can find many hooks over the internet, which all this also depends on the environment you're working on. If you're working on Node.js, there are libraries that actually install the hooks for you, and there are MPM modules that will do all that for you. So for example, JS lint, if you're working on JavaScript, it also comes with an MPM module that installs all the GitHub stuff for you. So you. Can you show some example of JS lint? Sorry? Can you show some example of JS lint? JS lint? Well, what sort of example are you looking for? How does it install it? OK. If you go into don't have access, but I don't have there any. It's the JS and the yellow pencil, I think, is the password. Send all the installments. So essentially, there are some MPM modules you could just reuse and install in your packages that would do that stuff for you. So you just MPM install that module, and it should be able to do it. Not really. So the thing is, if you are working on a particular environment, well, typically, if you want your script to be run on every of your team members' environments, it's recommended that you make sure the prerequisites of the environment are met. So you don't really, I haven't seen particular, if else, things that run on dependent environments. Like something that you can use like client-side hooks for all repositories? No, unfortunately, there's nothing like that. But typically, you need to install the hooks in every individual machine. Is there built-in support for running multiple hooks, or do you have to kind of write a wrapper or a script around it? Like if you want to run two different checks on a commit, you just have to, it gets only going to execute one executable? So it's essentially, for example, if I want to run two scripts in the pre-commit hook, it's essentially just a script. So you could just write different files if you want to separate it out, or write different modules, and so on. Can you show an example of how KSC works? Oh, well, let me, I don't have, actually, I have my company, but I doubt I can show it at this point. Seriously, seriously. Do you want to just create a new history at JSNS dependency when installed and created for the file? Sure. That's all. Anything else?