轻松创建拉取请求

首次向 fastai 提交拉取请求

要想为 fastai(或任何 fast.ai 库……甚至大多数开源软件!)贡献代码,你需要创建一个拉取请求(pull request),也称为 PR。这是一个拉取请求的示例。在这个例子中,你可以从描述中看到它是修复库中一些拼写错误。如果你点击该页面上的“Files changed”,你可以看到所有所做的更改。当拉取请求到达时,我们会收到通知,在检查更改是否没问题后,我们会将其“合并”(这意味着我们在 GitHub 中点击一个按钮,所有这些更改就会自动添加到仓库中)。

首次创建拉取请求可能会感到有些不知所措,所以我整理了本指南来帮助你入门。我们将使用 GitHub 的命令行工具 gh,它比通过网站操作更快更简单(至少我个人认为如此!)。要在 Linux 上安装 gh,请按照此处给出的说明进行操作。要在 Mac 上安装 gh,输入:brew install github/gh/gh

本指南假定你使用的是 Linux,并且已经安装了 AnacondaMiniconda。这是所有 fast.ai 课程指南中的默认设置,并且强烈推荐。它在 Mac 上应该也能正常工作,尽管我没有测试过。在 Windows 上,请使用 WSL 上的 Ubuntu

本文档是从 Jupyter Notebook 生成的。你可以从此处获取并自己运行该 Notebook。你需要安装 Jupyter Bash kernel

一次性设置

设置访问和 gh

要开发 fastai,你需要安装 fastainbdev(如果已安装,此命令也会检查你是否拥有最新版本)

conda install -y -c fastai -c pytorch -c anaconda anaconda fastai nbdev
Collecting package metadata (current_repodata.json): done

注意:如果你使用的是 Miniconda 而不是 Anaconda,请从上述命令中删除 -c anaconda anaconda

nbdev 是一个真正的文学编程框架;请参阅这篇文章,了解为什么你应该考虑在下一个项目中使用它(以及为什么我们在 fastai 中使用它)。

如果你还没有设置 ssh 访问 GitHub,则需要进行设置。为此,请按照这些步骤操作。创建 ssh 密钥后(通常通过运行 ssh-keygen),你可以复制你的 .~/ssh/id_rsa.pub 文件内容,然后通过在此页面上点击“New SSH Key”将其粘贴到 GitHub 中。

一旦设置好,我们需要获取一个个人访问令牌,以便 gh 连接到 GitHub。为此,请点击此处,在“Note”部分输入“gh”,然后选中 reporead:discussionread:org 复选框(请注意,gh 可以自动为你完成此操作,但这仅在你本地机器上运行代码时才方便;大多数 fastai 开发者可能使用远程 GPU 服务器,例如 Paperspace、AWS 或 GCP,因此我们在下方展示的方法适用于所有人)。

Personal access token screen

然后点击屏幕底部的“Generate Token”,并复制该令牌(显示的长串字母和数字)。你可以通过点击令牌旁边的小剪贴板图标轻松完成此操作。

Copying your token

现在在你的 shell 中运行此命令,将 jph01 替换为你的 GitHub 用户名,并将 TOKEN= 后面的字符串替换为你复制的令牌

GH_USER=jph01
TOKEN=abae9e225efcf319f41c68f3f4d7c2d92f59403e

设置 gh 使用 ssh 连接到 GitHub,这样你就不必总是输入你的姓名和密码

gh config set git_protocol ssh

创建你的 GitHub 认证文件

echo -e "github.com:\n  user: $GH_USER\n  oauth_token: $TOKEN\n" > ~/.config/gh/hosts.yml

设置 fastcore

现在我们准备克隆 fastcorefastai 库。我们建议克隆这两个库,因为你可能需要在 fastai 大量使用的 fastcore 库中进行更改或调试。首先,我们来处理 fastcore

gh repo clone fastai/fastcore
Cloning into 'fastcore'...
remote: Enumerating objects: 247, done.
remote: Counting objects: 100% (247/247), done.
remote: Compressing objects: 100% (164/164), done.
remote: Total 1618 (delta 162), reused 139 (delta 78), pack-reused 1371
Receiving objects: 100% (1618/1618), 3.18 MiB | 18.61 MiB/s, done.
Resolving deltas: 100% (1102/1102), done.

我们更新已安装的版本以使用可编辑模式。这意味着你对你检出的仓库中的代码所做的任何更改都将在你计算机上使用此库的所有位置自动生效

cd fastcore
pip install -qe .

我们更新仓库以创建和使用分支 (fork)

gh repo fork --remote
- Forking fastai/fastcore...
! jph01/fastcore already exists
✓ Renamed origin remote to upstream
✓ Added remote origin

因为所有的 fast.ai 库都使用 nbdev,所以我们在克隆仓库后第一次需要运行nbdev_install_hooks;这确保了每当我们推送到 GitHub 时,我们的 Notebook 都会自动清理并被信任

nbdev_install_hooks
Executing: git config --local include.path ../.gitconfig
Success: hooks are installed and repo's .gitconfig is now trusted

设置 fastai

现在我们对 fastai 执行相同的步骤

cd ..
gh repo clone fastai/fastai
cd fastai
Cloning into 'fastai'...
remote: Enumerating objects: 108, done.
remote: Counting objects: 100% (108/108), done.
remote: Compressing objects: 100% (79/79), done.
remote: Total 10206 (delta 41), reused 57 (delta 27), pack-reused 10098
Receiving objects: 100% (10206/10206), 536.85 MiB | 38.67 MiB/s, done.
Resolving deltas: 100% (8053/8053), done.
Already up to date.

我们也将以可编辑模式安装 fastai

pip install -qe .[dev]

……并分支 (fork) 它并安装 git 钩子

gh repo fork --remote
- Forking fastai/fastai...
! jph01/fastai already exists
✓ Renamed origin remote to upstream
✓ Added remote origin
nbdev_install_hooks
Executing: git config --local include.path ../.gitconfig
Success: hooks are installed and repo's .gitconfig is now trusted

创建你的 PR

以上所有步骤只需执行一次。接下来是实际创建 PR 的命令。

通过运行以下命令创建一个新的git 分支,将 test-pr 替换为你想要给拉取请求起的名称(请使用一个将来你需要更新 PR 时容易记住的名称)

git checkout -b test-pr
M   docs
Switched to a new branch 'test-pr'

在 Notebook 中进行你想要进行的任何更改,并在完成后记住运行 nbdev_build_lib,以确保库是根据你的 Notebook 更改构建的(除非你只更改了 Markdown,在这种情况下则不需要)。检查 git diff 的输出也是个好主意,以确保你没有意外地做出超出计划的更改。

准备就绪后,提交 (commit) 你的工作,将此处的“just testing”替换为你提交内容的清晰描述

git commit -am "just testing"
[test-pr 3397cc9] just testing
 2 files changed, 2 insertions(+), 1 deletion(-)

第一次从你的分支推送时,你需要添加 -u origin HEAD,但第一次之后,你只需使用 git push 即可。

git push -u origin HEAD
Counting objects: 4, done.
Delta compression using up to 64 threads.
Compressing objects: 100% (4/4), done.
Writing objects: 100% (4/4), 383 bytes | 383.00 KiB/s, done.
Total 4 (delta 3), reused 0 (delta 0)
remote: Resolving deltas: 100% (3/3), completed with 3 local objects.
remote: 
remote: Create a pull request for 'test-pr' on GitHub by visiting:
remote:      https://github.com/jph01/fastai/pull/new/test-pr
remote: 
To github.com:jph01/fastai.git
 * [new branch]      HEAD -> test-pr
Branch 'test-pr' set up to track remote branch 'test-pr' from 'origin'.

现在你已准备好创建 PR。要使用你的提交消息作为 PR 标题,只需运行

gh pr create -f
https://github.com/fastai/fastai/pull/2664

要交互式地提示输入更多信息(包括打开编辑器让你填写详细描述),只需运行 gh pr create 而不带 -f 标志。正如你上面看到的,完成后它会打印新 PR 的 URL - 恭喜你,感谢你的贡献!

The completed pull request

PR 后步骤

要使你的分支与 fastai 主仓库的更改保持同步,并将你的 test-pr 分支切换回 master 分支,运行

git pull upstream master
git checkout master
From github.com:fastai/fastai
 * branch            master     -> FETCH_HEAD
Already up to date.
M   docs
Switched to branch 'master'
Your branch is up to date with 'upstream/master'.

将来,一旦你的 PR 已合并或被拒绝,如果你不再需要该分支,则可以将其删除

git branch -d test-pr
Deleted branch test-pr (was 514782a).
(base) 
: 1