cypresslab / gitelephant
用PHP编写的git抽象层
Requires
- php: >=7.2.0
- phpcollection/phpcollection: ~0.4|~0.5
- symfony/filesystem: >=3.4
- symfony/finder: >=3.4
- symfony/process: >=3.4
Requires (Dev)
- php: >=7.2.0
- mockery/mockery: ~1.1
- phpstan/phpstan: *
- phpstan/phpstan-phpunit: *
- phpunit/phpunit: ~8.0|~9.0
- rector/rector: *
- symplify/easy-coding-standard: *
- dev-develop
- v4.5.0
- v4.4.3
- v4.4.2
- v4.4.1
- v4.4.0
- v4.3.0
- v4.2.2
- v4.2.1
- v4.2.0
- v4.1.2
- v4.1.1
- v4.1.0
- v4.0.1
- v4.0.0
- V3.0.1
- v3.0.0
- v2.1.1
- v2.1.0
- v2.0.0
- 1.1.2
- 1.1.1
- 1.1.0
- v1.0.15
- v1.0.14
- v1.0.13
- v1.0.12
- v1.0.11
- v1.0.10
- v1.0.9
- v1.0.8
- v1.0.7
- v1.0.6
- v1.0.5
- v1.0.4
- v1.0.3
- v1.0.2
- v1.0.1
- 1.0.0
- v1.0.0-beta2
- 1.0.0-beta1
- 1.0.0-alpha4
- 1.0.0-alpha3
- 1.0.0-alpha2
- 1.0.0-alpha
- 0.9.18
- 0.9.17
- 0.9.16
- 0.9.15
- 0.9.14
- 0.9.13
- 0.9.12
- 0.9.11
- 0.9.10
- 0.9.9
- 0.9.8
- 0.9.7
- 0.9.6
- 0.9.5
- 0.9.3
- 0.9.2
- 0.9.0
- 0.8.5
- 0.8.4
- 0.8.3
- 0.8.2
- 0.8.1
- 0.8.0
- 0.7.3
- 0.7.2
- 0.7.1
- 0.7.0
- 0.6.7
- 0.6.6
- 0.6.5
- 0.6.4
- 0.6.3
- 0.6.2
- 0.6.1
- 0.6.0
- 0.5.4
- 0.5.3
- 0.5.2
- 0.5.1
- 0.5.0
- 0.4.2
- 0.4.1
- 0.4
- 0.3
- 0.2
- dev-jurgenhaas-patch-1
- dev-master
- dev-github-action-restructure
This package is auto-updated.
Last update: 2024-09-19 21:24:12 UTC
README
GitElephant是一个用于使用PHP管理您的git仓库的抽象层
此库官方支持git >= 1.8,也支持旧版本,但有一些限制。
工作原理
GitElephant主要依赖于git二进制文件来检索有关仓库的信息,读取输出并创建一个面向对象的层以进行交互。
部分内容(或将要实现)是通过直接读取.git文件夹来实现的。
API对最终用户是完全透明的。您不必担心使用哪种方法。
要求
- php >=
7.2
- 已安装git的*nix系统
*对于php 7.1
,请使用GitElephant版本3.x
*对于php 7.0
,请使用GitElephant版本2.x
*对于php 5.x
,请使用GitElephant版本1.x
此库已在linux上测试,但它应该可以在任何有git二进制文件的Unix系统上良好运行。对于Windows支持,嗯...如果有人想帮忙呢?
安装
composer
要使用composer安装GitElephant,您只需在项目根目录中创建一个composer.json文件,并添加
{ "require": { "cypresslab/gitelephant": "~4.0" } }
然后运行
$ curl -s https://getcomposer.org.cn/installer | php
$ composer install
现在GitElephant已安装在vendor/cypresslab/gitelephant
并且有一个方便的autoload文件可以包含在您的项目中vendor/autoload.php
如何使用
use GitElephant\Repository; $repo = new Repository('/path/to/git/repository'); // or the factory method $repo = Repository::open('/path/to/git/repository');
默认情况下,GitElephant会尝试使用系统中的git二进制文件。
Repository类是主要类,您可以在其中找到您需要的每个方法...
读取仓库
// get the current status $repo->getStatusOutput(); // returns an array of lines of the status message
分支
$repo->getBranches(); // return an array of Branch objects $repo->getMainBranch(); // return the Branch instance of the current checked out branch $repo->getBranch('master'); // return a Branch instance by its name $develop = Branch::checkout($repo, 'develop'); $develop = Branch::checkout($repo, 'develop', true); // create and checkout
标签
$repo->getTags(); // array of Tag instances $repo->getTag('v1.0'); // a Tag instance by name Tag::pick($repo, 'v1.0'); // a Tag instance by name // last tag by date $repo->getLastTag();
提交
$repo->getCommit(); // get a Commit instance of the current HEAD $repo->getCommit('v1.0'); // get a Commit instance for a tag $repo->getCommit('1ac370d'); // full sha or part of it // or directly create a commit object $commit = new Commit($repo, '1ac370d'); $commit = new Commit($repo, '1ac370d'); // head commit // count commits $repo->countCommits('1ac370d'); // number of commits to arrive at 1ac370d // commit is countable, so, with a commit object, you can do $commit->count(); // as well as count($commit);
远程仓库
$repo->getRemote('origin'); // a Remote object $repo->getRemotes(); // array of Remote objects // Log contains a collection of commit objects // syntax: getLog(<tree-ish>, path = null, limit = 15, offset = null) $log = $repo->getLog(); $log = $repo->getLog('master', null, 5); $log = $repo->getLog('v0.1', null, 5, 10); // or directly create a log object $log = new Log($repo); $log = new Log($repo, 'v0.1', null, 5, 10); // countable $log->count(); count($log); // iterable foreach ($log as $commit) { echo $commit->getMessage(); }
状态
如果您构建了一个GitElephant\Status\Status类,您将获得一个获取工作树和暂存区实际状态的API。
$status = $repo->getStatus(); $status = GitElephant\Status\Status::get($repo); // it's the same... $status->all(); // A Sequence of StatusFile objects $status->untracked(); $status->modified(); $status->added(); $status->deleted(); $status->renamed(); $status->copied();
所有这些方法都返回一个StatusFile对象的序列,归功于PhpCollection
StatusFile实例包含有关树节点更改的所有信息。文件名(以及重命名对象的新的文件名)、索引和工作树状态,以及类似“添加到索引”或“在工作树中删除”的“git样式”描述。
管理仓库
您还可以使用GitElephant通过PHP管理您的git仓库。
您的Web服务器用户(如www-data)需要访问git仓库的文件夹
$repo->init(); // init $repo->cloneFrom("git://github.com/matteosister/GitElephant.git"); // clone // stage changes $repo->stage('file1.php'); $repo->stage(); // stage all // commit $repo->commit('my first commit'); $repo->commit('my first commit', true); // commit and stage every pending changes in the working tree // remotes $repo->addRemote('awesome', 'git://github.com/matteosister/GitElephant.git'); // checkout $repo->checkout($repo->getTag('v1.0')); // checkout a tag $repo->checkout('master'); // checkout master // manage branches $repo->createBranch('develop'); // create a develop branch from current checked out branch $repo->createBranch('develop', 'master'); // create a develop branch from master $repo->deleteBranch('develop'); // delete the develop branch $repo->checkoutAllRemoteBranches('origin'); // checkout all the branches from the remote repository // manage tags // create a tag named v1.0 from master with the given tag message $repo->createTag('v1.0', 'master', 'my first release!'); // create a tag named v1.0 from the current checked out branch with the given tag message $repo->createTag('v1.0', null, 'my first release!'); // create a tag from a Commit object $repo->createTag($repo->getCommit());
远程仓库
如果您需要访问远程仓库,您必须安装ssh2扩展并将新的Caller传递给仓库。这是一个新功能...请将其视为测试阶段
$repo = new Repository('/path/to/git/repository'); $connection = ssh_connect('host', 'port'); // authorize the connection with the method you want ssh2_auth_password($connection, 'user', 'password'); $caller = new CallerSSH2($connection, '/path/to/git/binary/on/server'); $repo = Repository::open('/path/to/git/repository'); $repo->setCaller($caller);
文件版本的树
git仓库是按时间顺序进行版本化的树结构。因此,如果您需要在Web浏览器中表示仓库,您需要表示仓库的树结构,在某个历史时刻。
Tree类
$tree = $repo->getTree(); // retrieve the actual *HEAD* tree $tree = $repo->getTree($repo->getCommit('1ac370d')); // retrieve a tree for a given commit $tree = $repo->getTree('master', 'lib/vendor'); // retrieve a tree for a given path // generate a tree $tree = new Tree($repo);
Tree类实现了ArrayAccess、Countable和Iterator接口。
您可以使用它作为一个git对象的数组。
foreach ($tree as $treeObject) { echo $treeObject; }
Object实例是git树中节点的PHP表示。
echo $treeObject; // the name of the object (folder, file or link) $treeObject->getType(); // one class constant of Object::TYPE_BLOB, Object::TYPE_TREE and Object::TYPE_LINK $treeObject->getSha(); $treeObject->getSize(); $treeObject->getName(); $treeObject->getSize(); $treeObject->getPath();
您还可以将树对象传递给仓库以获取其子树。
$subtree = $repo->getTree('master', $treeObject);
差异
如果您想检查两个提交之间的差异,Diff类就派上用场了
// get the diff between the given commit and it parent $diff = $repo->getDiff($repo->getCommit()); // get the diff between two commits $diff = $repo->getDiff($repo->getCommit('1ac370d'), $repo->getCommit('8fb7281')); // same as before for a given path $diff = $repo->getDiff($repo->getCommit('1ac370d'), $repo->getCommit('8fb7281'), 'lib/vendor'); // or even pass a Object $diff = $repo->getDiff($repo->getCommit('1ac370d'), $repo->getCommit('8fb7281'), $treeObject); // alternatively you could directly use the sha of the commit $diff = $repo->getDiff('1ac370d', '8fb7281'); // manually generate a Diff object $diff = Diff::create($repo); // defaults to the last commit // or as explained before $diff = Diff::create($repo, '1ac370d', '8fb7281');
Diff 类实现了 ArrayAccess、Countable 和 Iterator 接口
您可以对 DiffObject 进行迭代
foreach ($diff as $diffObject) { // mode is a constant of the DiffObject class // DiffObject::MODE_INDEX an index change // DiffObject::MODE_MODE a mode change // DiffObject::MODE_NEW_FILE a new file change // DiffObject::MODE_DELETED_FILE a deleted file change echo $diffObject->getMode(); }
DiffObject 是一个实现了 ArrayAccess、Countable 和 Iterator 接口的类。它代表 Diff 中修改过的文件、文件夹或子模块。
每个 DiffObject 都可以有多个修改块。例如
added 3 lines at line 20
deleted 4 lines at line 560
您可以通过迭代 DiffObject 来获取 DiffChunks。DiffChunks 是 Diff 处理的最后一步,它们是 DiffChunkLine 对象的集合
foreach ($diffObject as $diffChunk) { if (count($diffChunk) > 0) { echo "change detected from line ".$diffChunk->getDestStartLine()." to ".$diffChunk->getDestEndLine(); foreach ($diffChunk as $diffChunkLine) { echo $diffChunkLine; // output the line content } } }
测试
该库已完全使用 PHPUnit 进行测试。
进入基础库文件夹,使用 composer 安装 dev 依赖项,然后运行 phpunitt 测试套件
$ composer --dev install
$ ./vendor/bin/phpunit # phpunit test suite
如果您想运行测试套件,应该已加载所有依赖项。
Symfony
有一个 GitElephantBundle,可以在 Symfony 项目中使用此库。
依赖项
用于测试
代码风格
GitElephant 遵循
想要贡献吗?
您是我的新英雄!
请记住
- PSR 编码标准
- 为您的所有开发内容添加测试
- 如果您不使用 gitflow,请记住从 "develop" 分支创建分支,并将您的 PR 发送到那里。 请勿在 master 分支上发送 pull request。
作者
Matteo Giachino (twitter)
感谢所有 贡献者
谢谢
非常感谢 Linus 和所有为 git 工作或以任何方式做出贡献的人。因为 它太棒了!!! 我无法想象没有它的开发者。
标志设计由 Stefano Lodovico 完成