我们来学一下如何PR
以我当时第一次PR给forever218大佬的hexo magzine主题为例
虽然我用AI把他的项目改的面目全非,不过大佬每次都接纳了......感觉有时间还得再看看不过确实学到了很多新知识,非常感谢大佬,因为借助他设计的blog我也接触到和吸引到了很多大佬
PR用到的相关命令
| 功能 | 命令(新 Git 写法) | 命令(旧 Git 写法) | 说明 |
|---|---|---|---|
| 克隆仓库 | git clone <仓库地址> | 同上 | 克隆远程仓库到本地 |
| 进入项目 | cd <项目文件夹> | 同上 | 进入本地仓库 |
| 查看远程 | git remote -v | 同上 | 查看 origin/upstream 等远程地址 |
| 添加上游 | git remote add upstream <地址> | 同上 | 第一次配置原作者仓库,地址是HTTPS或SSH |
| 修改远程地址 | git remote set-url <name> <地址> | 同上 | 改 SSH/HTTPS,或更新远程地址,name一般为origin/upstream |
| 切换到已有分支 | git switch dev | git checkout dev | 切换本地已有分支 |
| 创建并切换新分支 | git switch -c 分支名 | git checkout -b 分支名 | 基于当前分支创建新分支并切换过去 |
| 查看当前状态 | git status | 同上 | 查看修改、暂存和分支状态 |
| 查看改动内容 | git diff | 同上 | 查看未暂存的改动 |
| 查看暂存区改动 | git diff --cached | 同上 | 查看已 add 但未提交的内容 |
| 暂存改动 | git add . | 同上 | 把所有改动加入暂存区 |
| 提交改动 | git commit -m "说明" | 同上 | 提交到本地仓库 |
| 拉取远程分支信息 | git fetch upstream | 同上 | 获取上游分支更新,不合并 |
| 合并远程分支到本地 | git merge upstream/dev | 同上 | 把上游 dev 合并到本地分支 |
| 推送到远程 | git push -u origin 分支名 | 同上 | -u 建立跟踪关系,可选;首次推送新分支建议加 |
| 推送已有分支 | git push | 同上 | 如果分支已和远程跟踪,直接推送即可 |
| 查看分支列表 | git branch | 同上 | 查看本地所有分支,* 表示当前分支 |
| 查看分支和远程跟踪关系 | git branch -vv | 同上 | 显示本地分支和对应远程分支、最后提交 |
| 查看远程分支 | git branch -r | 同上 | 显示远程分支列表 |
| 查看本地 + 远程分支 | git branch -a | 同上 | 显示所有分支 |
| 删除分支 | git branch -d <分支> / git push origin --delete <分支> | 同上 | 清理完成的分支 |
这里有几个注意点
git push -u origin 分支名
-u 等同于 --set-upstream,用于建立本地分支和远程分支的跟踪关系
示例:
git push -u origin fix-imagezoom
- 这里的意思是:
- 把本地
fix-imagezoom分支推到origin上 - 同时告诉 Git:以后本地
fix-imagezoom默认跟踪远程origin/fix-imagezoom
- 把本地
- 后续再推送或拉取时,只需要:
git push
git pull
Git 会自动知道你想推/拉 origin/fix-imagezoom。
如果不加 -u:推送也能成功,但以后每次都得写:
git push origin fix-imagezoom
git pull origin fix-imagezoom
需要遵循的规范---Conventional Commits(约定式提交)
可能踩到的坑---github多账号ssh混淆
由于我github有两个账号即huyangpahuo和funingna-wakawaka,之前在两个账号都创建了ssh就遇到这个问题
你可以在C:\Users\用户名\.ssh找到它们
- 其中有一个
config,用于存储配置 - 以及私钥
id_rsa和公钥id_rsa.pub,用于远程连接(当然名字不一定是这个,默认创建都是id_rsa) - 还有一个
known_hosts,用于在客户端存储已连接过的远程服务器的公钥,从而验证服务器的身份并防止中间人攻击 - 有的时候会出现
known_hosts.old文件,一般可以删掉因为这个只是对known_hosts更新后的备份
这个是在git bash里使用如下命令生成的
git config --global user.name "GitHub用户名"
git config --global user.email "GitHub邮箱"
ssh-keygen -t rsa -C "GitHub邮箱"
当然你也可以验证一下
#查看用户名:
git config user.name
#查看邮箱:
git config user.email
其中私钥绝不能泄露,公钥则需要粘贴到github里的ssh配置区
但是当我们使用
ssh git@github.com
得到funingna-wakawaka
PTY allocation request failed on channel 0
Hi funingna-wakawaka! You've successfully authenticated, but GitHub does not provide shell access.
Connection to github.com closed.
同样的也是
ssh -T git@github.com
得到funingna-wakawaka
Hi funingna-wakawaka! You've successfully authenticated, but GitHub does not provide shell access.
甚至使用git@github.com:huyangpahuo/hexo-theme-magzine.git时也是funingna-wakawaka
我们使用这个打印出所有配置的参数
ssh -G git@github.com
可以看到用的是22端口而非github默认的443端口
host github.com
user git
hostname github.com
port 22
addressfamily any
batchmode no
canonicalizefallbacklocal yes
......
这说明一个问题,此时github是自动使用的是funingna-wakawaka,而我们如果要使用huyangpahuo的账号就不能再使用git@github.com这种写法
解决方法
不过假设你和我一样不小心配置了一堆github ssh甚至对应的账号不同例如rsa_second,rsa_third
ssh-keygen -t rsa_second -C "GitHub邮箱"
ssh-keygen -t rsa_third -C "GitHub邮箱"
那么就需要修改config文件(如果你只有一个那就不用改默认即可)
# Global defaults (safe)
Host *
ServerAliveInterval 30
ServerAliveCountMax 120
AddKeysToAgent no
IdentitiesOnly yes
# Account 1: funingna-wakawaka
Host github-funingna
HostName ssh.github.com
Port 443
User git
IdentityFile ~/.ssh/id_rsa # funingna key
IdentitiesOnly yes
# Account 2: huyangpahuo
Host github-huyang-01
HostName ssh.github.com
Port 443
User git
IdentityFile ~/.ssh/id_rsa_second # huyang key
IdentitiesOnly yes
# Account 3: huyangpahuo
Host github-huyang-02
HostName ssh.github.com
Port 443
User git
IdentityFile ~/.ssh/id_rsa_third # huyang key
IdentitiesOnly yes
相关参数
| 参数 | 作用 | 当前的值 |
|---|---|---|
Host | 定义一组连接规则/别名 | *、github-funingna |
HostName | 真正要连接的服务器地址 | ssh.github.com |
Port | SSH 连接端口 | 443 |
User | 登录时使用的用户名 | git |
IdentityFile | 指定使用的 SSH 私钥 | ~/.ssh/id_rsa |
IdentitiesOnly | 是否只使用明确指定的密钥 | yes |
ServerAliveInterval | 多久发送一次 SSH 保活请求 | 30 秒 |
ServerAliveCountMax | 保活失败多少次后断开 | 120 |
AddKeysToAgent | 是否自动把私钥加入 SSH Agent | no |
这里我分别为三个ssh取别名为github-funingna ,github-huyang-01,github-huyang-02表示这是github的ssh
并分别指定对应的私钥文件
ssh验证
我们必须用git@github-huyang-01:huyangpahuo/hexo-theme-magzine.git这种指定别名的方式才能验证
我们可以用ssh验证
ssh git@github-huyang-01
得到huyangpahuo
PTY allocation request failed on channel 0
Hi huyangpahuo! You've successfully authenticated, but GitHub does not provide shell access.
Connection to ssh.github.com closed.
也就是我们要使用的这个
PR实例
这里我们分成好几种情况,由于这个仓库有两个分支,一个叫做master(主分支),一个叫做dev(实验分支)
主分支是正式版本,副分支为实验版本
首先先复刻仓库并clone复刻仓库的项目到本地
# 克隆你 fork 的仓库
git clone git@github-huyang-01:huyangpahuo/hexo-theme-magzine.git
cd hexo-theme-magzine
# 添加 upstream(原作者仓库)
git remote add upstream git@github-huyang-01:forever218/hexo-theme-magzine.git
# 查看远程仓库是否正确
git remote -v
一,PR到原作者仓库的Main/Master主分支(例如Master)
二,PR到原作者仓库的其他副分支(例如Dev)
① 只同步和维护自己 fork 的分支(例如dev)
情况 A:本地和远程都没有同步(第一次更新或本地删除过)
# 创建并切换到本地 dev,跟踪 upstream/dev
git switch -c dev --track upstream/dev
# 老写法:git checkout -b dev --track upstream/dev
# 把本地 dev 推到你的 fork(第一次)
git push -u origin dev
情况 B:本地 dev 已经存在,远程 fork dev 已同步(继续维护)
# 切换到本地 dev
git switch dev
# 老写法:git checkout dev
# 拉取 upstream 最新 dev
git fetch upstream
git merge upstream/dev
然后修改上传到自己复刻的仓库
# --- 开始开发 ---
# 修改项目文件
# 改完查看状态
git status
git diff # 可选:查看未暂存改动
# 暂存改动
git add .
# 查看已暂存内容(可选)
git diff --cached
# 提交到本地 dev
git commit -m "更新说明"
# 推送到你的 fork dev
git push
② 给作者发 PR 的流程
情况 A:本地和远程都没有同步(第一次做 PR)
# 创建并切换本地 dev
git switch -c dev --track upstream/dev
# 老写法:git checkout -b dev --track upstream/dev
# 更新到最新 dev
git fetch upstream
git merge upstream/dev
git push -u origin dev # 更新 fork 的 dev(可选)
# 基于最新 dev 创建新功能分支
git switch -c 你的新分支名
# 老写法:git checkout -b 你的新分支名
情况 B:本地 dev 已存在,远程 fork dev 已同步(继续做 PR)
# 切换到本地 dev
git switch dev
# 老写法:git checkout dev
# 拉取 upstream 最新 dev
git fetch upstream
git merge upstream/dev
# 基于 dev 创建新功能分支
git switch -c 你的新分支名
# 老写法:git checkout -b 你的新分支名
然后修改上传
# --- 开始开发 ---
git status
git diff
git add .
git diff --cached
git commit -m "更新说明"
# 推送功能分支到 fork
git push -u origin 你的新分支名
上传之后若作者合并了,此时可以在github里删除掉这个分支,然后更新自己复刻的仓库即可
# 在 GitHub 上发 PR,PR 合并后删分支,当然最好在Github里删除,不要使用命令行
git switch dev #切到dev分支
git branch -d 你的新分支名 # 删除本地分支
git push origin --delete 你的新分支名 # 删除远程分支