husky: 'husky install' fails if '.git' directory does not exists

I have a postinstall script in a NPM package:

"postinstall": "is-ci || husky install",

If I download the repository using Github UI (Code -> Download ZIP), after extracting it, executing npm install raises Error: .git can't be found:

postinstall error
> simple-icons-font@4.9.0 postinstall /.../simple-icons-font-develop
> is-ci || husky install

/.../simple-icons-font-develop/node_modules/husky/lib/commands/install.js:20
        throw new Error(".git can't be found");
        ^

Error: .git can't be found
    at Object.install (/.../simple-icons-font-develop/node_modules/husky/lib/commands/install.js:20:15)
    at Object.<anonymous> (/.../simple-icons-font-develop/node_modules/husky/lib/bin.js:43:19)

I can prevent the error doing something like this:

"postinstall": "node -e \"if(require('fs').existsSync('.git')){process.exit(1)}\" || is-ci || husky install",

But it seems a bit hacky. What would be the recommended way to solve this?

About this issue

  • Original URL
  • State: closed
  • Created 3 years ago
  • Reactions: 25
  • Comments: 58 (5 by maintainers)

Commits related to this issue

Most upvoted comments

The case you may be in is if your package.json file and .git directory are not at the same level. For example, project/.git and project/front/package.json.

By design, husky install must be run in the same directory as .git, but you can change directory during prepare script and pass a subdirectory:

Change script in package.json to this: // package.json { “scripts”: { “prepare”: “cd … && husky install front/.husky” } }

Then do npm install to fix it

I am having this same issue when trying to install husky on a repo where I have multiple projects and the .git file is up a directory. Are there configuration options for this use case? I have two projects with node modules nested inside one git repo for the sanity CMS and the Gatsby FE.

image

Please, stop mention me in this issue. It was fixed 3 major versions ago and I’ve not experienced it more.

Any updates on this? For 8.x fails if .git folder is in the parent directory

I’m running v5.0.9 and am getting this error 😦

throw new Error(".git can't be found");

The bug still exists in 7.0.4, could you please place a recursive test to check if the .git folder exists in the parent, then parent’s parent, then parent’s parent’s parent… folder.

In the real world, it happens that the GIT is a mono-repo that contains differents folders with different projects with a package.json in each.

I can see that, but the error is preventing the installation of the husky package in the first place, so that workaround doesn’t help me with that.

You have to add the modified version of the prepare script before installing husky, so that the Husky install knows where to put the files. The hint from the docs that helped me was:

If your package.json is not at the same level as .git, please update manually. […] husky init sets up Git hooks and updates your package.json scripts (you may want to commit your changes to package.json before running husky init).

Since husky init is called as part of the install process (which is what triggers this error), the implication is that the edits must be made before installation.

I just did it on a second project, where the frontend is in App. Here were the exact steps:

  • Edit App/package.json to include husky as a devDependency
  • Add the prepare script: cd .. && husky install App/.husky
  • Run yarn install

As you can see, the prepare script is run after the yarn package is installed, but before Husky complains about the path:

Screen Shot 2021-06-10 at 11 52 52 AM

Hi @mondeja,

Thanks for the report. It’s fixed in v5.0.9. If not in a git repo, Git will simply output a message and not fail.

"scripts": {
    "prepare": "cd .. && husky installtemplate/.husky",
...
    }

this worked for me

You can do HUSKY=0 yourCommand and it should work.

Can’t seem to reproduce, here’s how I’m testing:

$ cd /tmp
$ mkdir foo && cd foo
$ npm init -y
$ npm install husky -D
$ npx husky install
husky - not a Git repository, skipping hooks installation

Is your package.json in a nested directory compared to .git? If that’s the case, see https://typicode.github.io/husky/#/?id=custom-directory

Otherwise could you provide minimal steps for me to reproduce (or a repo)?

I’m running 7.0.4 and this issue is happening for me.

I’m also having this issue, granted, the codebase I’m trying to install this to is a frontend that’s a folder inside the main repo.

Is there any updates on this matter ?

I am seeing the same issue with v7.0.0 when trying to execute husky install in a Docker container. Is there maybe a possible regression?

Bildschirmfoto 2021-07-06 um 09 08 52

We get the issue when we use a repo as a dependency. e.g. in package.json: "ourapp": "git+ssh://git@github.com/myproject/ourapp.git#v9.1.3",

For more information on how this works see: https://docs.npmjs.com/cli/v6/commands/npm-install Screen Shot 2021-02-11 at 1 06 48 PM

We have followed the advice to use pinst to work around this issue:

"scripts": {
    "postinstall": "husky install",
    "prepublishOnly": "pinst --disable",
    "postpublish": "pinst --enable"
  }

But get the error when installing the updated version:

throw new Error(".git can't be found");

Are there any updates on this? I have the same behavior. husky 7.0.0 with package.json and .git at the same level. I also tried without husky (removing “prepare”: “husky install” from scripts) but same problem. Thanks Screenshot 2022-06-09 at 09 16 26

I have solved the issue. Steps mentioned below,

  1. delete .git folder from your home directory in my case it is users/sandeeprajbhar/.git
  2. then run : npx husky-init && yarn

Hi @mondeja,

Thanks for the report. It’s fixed in v5.0.9. If not in a git repo, Git will simply output a message and not fail.

Hi I have the same problem in v6 😕

I experienced the same issue, but was able to resolve it by converting my postinstall script to prepare instead.

Hi - I’m currently getting this same issue with a prepare: husky install npm script throwing the .git not found error when trying to run sam build - because the sam cli runs npm i in the container but the container doesn’t have a .git. I’m using husky v 6.0.0. Adding mondeja’s original hack works, but it is pretty hacky.

Hi,

To generate .husky folder, we can approach the below line of code in the script tag for any nested project folder

“prepare”: “cd …/…/ && husky install .husky”,

Regards, -Bechar

I have the same problem in version ^7.0.4

Should I try this workaround

The case you may be in is if your package.json file and .git directory are not at the same level. For example, project/.git and project/front/package.json.

By design, husky install must be run in the same directory as .git, but you can change directory during prepare script and pass a subdirectory:

Change script in package.json to this: // package.json { "scripts": { "prepare": "cd .. && husky install front/.husky" } }

Then do npm install to fix it

Thanks it worked

?

This is still an error in 7.x. My .git and package.json are at the same level.

Having the same issue in 7.0.2.

@dylanesque that use-case is documented on the project homepage itself. Tested & working well for me.

image

image

husky/lib/index.js

function install(dir = '.husky') {
    if (process.env.HUSKY === '0') {
        l('HUSKY env variable is set to 0, skipping install');
        return;
    }
    if (git(['rev-parse']).status !== 0) {
        l(`git command not found, skipping install`);
        return;
    }
    const url = 'https://typicode.github.io/husky/#/?id=custom-directory';
    if (!p.resolve(process.cwd(), dir).startsWith(process.cwd())) {
        throw new Error(`.. not allowed (see ${url})`);
    }
    if (!fs.existsSync('.git')) {
        throw new Error(`.git can't be found (see ${url})`);
    }
    try {
        fs.mkdirSync(p.join(dir, '_'), { recursive: true });
        fs.writeFileSync(p.join(dir, '_/.gitignore'), '*');
        fs.copyFileSync(p.join(__dirname, '../husky.sh'), p.join(dir, '_/husky.sh'));
        const { error } = git(['config', 'core.hooksPath', dir]);
        if (error) {
            throw error;
        }
    }
    catch (e) {
        l('Git hooks failed to install');
        throw e;
    }
    l('Git hooks installed');
}

So,the question maybe because the logic of git command not found, skipping install is not hit, where .git exists in the parent directory instead of the current directory.

So, the solution maybe is let git rev-parse just work in current directory, not searches upwards.

https://stackoverflow.com/questions/27177248/how-can-i-make-git-work-only-on-the-current-directory https://stackoverflow.com/questions/2545602/how-to-git-ignore-subfolders-subdirectories

Are there any updates on this? I have the same behavior. husky 7.0.0 with package.json and .git at the same level. I also tried without husky (removing “prepare”: “husky install” from scripts) but same problem. Thanks Screenshot 2022-06-09 at 09 16 26

Having the same issue in 7.0.1

Hitting this issue in 7.0.2

@typicode having the same issue with npm 7 (npm 6 is alright)

Having the same issue…

Trying to install via npm swagger-ui-react (swagger link) BUT im getting this error… - swagger-client@3.13.0 postinstall /front/node_modules/swagger-client - husky install throw new Error(".git can't be found");

as a devDependency husky installed… "husky": "^5.0.9",

if there is an option to fix that?