GIT push - remote:致命:此操作必须在工作树中运行

时间:2018-03-06 21:11:36

标签: git laravel version-control

我是GIT的新手。 我使用命令创建存储库:

cd /home/user_name
mkdir repo && cd repo
mkdir site.git && cd site.git
git init --bare

然后在hooks目录中创建post-receive文件并添加到那里:

#!/bin/sh
git --work-tree=/home/user_name/dev.ireserve.com --git-dir=/home/user_name/repo/site.git checkout -f

之后,我添加了权限:chmod +x post-receive

在我运行的laravel项目目录中的本地机器上:

git init

然后我跑:

git remote add live ssh://root@example.com/home/user_name/repo/site.git

之后通常会:

git add .
git commit -m "my message"

最后:

git push live master

但我收到了一条消息:

remote: fatal: This operation must be run in a work tree

enter image description here

为什么我收到此错误?有什么问题?

2 个答案:

答案 0 :(得分:2)

TL; DR:我认为您的Laravel设置说明中缺少mkdir步骤。

此命令:

git init --bare

用于制作服务器存储库,其中没有人会做任何工作

现在,这可能看起来很奇怪:为什么要创建一个无人可以在存储库上工作的存储库?并且 是一件奇怪的事情,但它存在是有原因的。

Bare vs non-bare repository

如果您创建了可以工作的存储库:

git init

那么你可以在其中工作,但是 - 过度简化了一点 - 没有其他人只是发送你的工作未经通知。但是人们还需要分享工作,一个常见的使用模式是每个人都同意某些中央服务器上的某些工作共享存储库,例如公司的“主源存储库”机器,应该是每个人都发送工作的地方。

但与此同时,您不希望有一个人花一整天时间将人们的工作带入该中央存储库。您希望让人们在工作完成后立即发送他们的工作,以便其他人可以立即前往中央存储库查看(甚至获取并使用)他们的工作 >。所以你需要一个人们可以发送他们的作品的地方,未经通知,现在

这是一个--bare存储库。由于没有人在其中工作,因此您不会通过发送已完成的工作来覆盖他们的正在进行的工作。

这真的是关于提交工作树

之间的区别

进行新的提交会使您的工作成为永久性且不易破坏的 1 快照。但它必须从某个地方获得这个。在其他版本控制系统中可以找到最小的“某处”作为工作树:您工作的地方。 Git在这里插入一个额外的皱纹,并强迫你知道它:它添加索引,也称为临时区域或有时缓存 (一件事就是三个名字 - 这是Git中一个非常重要的实体!)。索引和工作树成对出现:它们是你可以写东西的地方。一旦制成,提交完全是不可改变的,这使它们成为不腐败的。所以你需要一个工作的地方,你可以在那里读取和写文件。

裸存储库保存提交 - 只读快照 - 但没有工作树。 2 这就是它的全部内容:没有工作树,没有工作的地方。这就是它适合推送的原因,但没有工作的地方,你就无法做任何工作。您还需要一个非裸存储库。

1 提交实际上只是 永久性:只要有可以找到它们的名称,它们就会持续存在。我将把这个细节留给其他教程。但它们是完全不腐败的,因为提交的真实名称是它的哈希ID。哈希ID虽然预先不可预测,但是提交的内容的加密校验和。如果出现问题并且提交被破坏,Git会注意到,因为内容将不再适合真正的名称哈希ID。

2 由于某些愚蠢的实现原因,裸存储库仍然有一个索引。它没有工作树。它们是成对的 - 索引索引(因此名称)是工作树 - 但是一个裸存储库通常仍然有一个完全空的索引。

某些服务器为裸存储库伪造了工作树

您可以将裸存储库(没有工作树)与Git的 hooks 机制结合起来,创建一种虚假的工作树。例如,这就是您的Laravel设置的工作方式。当您的裸服务器收到git push时,服务器运行挂钩,挂钩运行git --work-tree=<path> checkout -f以在<path>中设置临时工作树。此临时工作树是一个git checkout命令持续时间的工作树。 (索引现在索引该临时工作树。)然后git checkout完成,裸存储库继续没有工作树。你仍然无法工作

请注意,最后git --work-tree=<path> checkout -f不会创建目录<path>。该目录必须已存在。它最初应该是空的;在第一个git checkout -f之后,它将包含git checkout写的内容;在每个后来git checkout -f,Git将假设(通过索引)它包含 last git checkout -f所写的内容,并根据此信息更新它。

因此,您的原始Laravel设置应该包含mkdir home/user_name/dev.ireserve.com

答案 1 :(得分:1)

从评论中,你有两个目录,你需要开始创建版本,这样你就可以使用GIT的真正力量。

如果您愿意使用GIT add,则需要创建分支(版本)。

检查此answer

添加分支,请检查此tutorial

这是start的教程。

这是最好的教程,恕我直言;对于GIT。

这将节省大量的精力和时间。

快乐的编码!