浅谈Git架构和如何避免代码覆盖的事故

news/2024/7/6 0:44:54

浅谈Git架构和如何避免代码覆盖的事故

Git 不同于 SVN 的地方在于, Git 是分布式的版本管理系统, 所有的客户端和服务器都保存了一份代码, 涉及到仓库仓之间的同步, 所以处理不当极易造成冲突

最直接的方法就是不让新手合并代码

  • PR 开发: GitHub 开源项目常用开发方式, 开发者在自己的 仓库 上开发, 完成后提交 PR 给管理员审核合并
  • MR 开发: 对代码要求比较严格的公司常用开发方式, 开发者在自己的 分支 上开发, 完成后提交 MR 给管理员审核合并

但是这样每次都要等管理员审核, 不适合敏捷开发的一般团队, 所以 Git 的学习和使用是必不可少的

Git架构

分布式的版本库

分布式的版本库

Git 本地仓库

Git本地的 3 个工作区

Git 本地仓库 + stash 贮藏区

Git本地的 3 个工作区 + stash 贮藏区

  • 使用 git stash 可以将 工作区和暂存区修改的文件 移动到贮藏区, 通常在本地存在不想提交的临时文件的时候 pull 之前使用
  • 使用 git stash pop 可以将贮藏区的文件恢复到 工作区和暂存区, 通常在提交之后使用

Git 本地仓库 + stash 贮藏区 + 远程仓库

Git 本地仓库 +  stash 贮藏区 + 远程仓库

常用命令

下面只是介绍下常见的开发命令, 其他命令可以参考 Git官方文档: https://git-scm.com/docs

共享分支开发

# 添加到暂存区
git add a.txt
# commit 本地仓库
git commit -m "新增 a.txt"
# 同步远程仓库
git pull origin master:master
# 推送到远程仓库
git push origin master:maser

非共享分支开发

提交到自己的远程分支, 然后提交 MR 合并到 master 分支

# 新建个人开发分支 dev_d
git branch dev_d
# 切换到个人开发分支 dev_d
git checkout dev_d
# 修改代码
# 添加到暂存区
git add a.txt
# commit 本地仓库
git commit -m "新增 a.txt"
# 同步远程仓库 master 副本并 merge 到 dev_d 分支
git pull origin master:master
# 推送本地 dev_d 分支到远程 dev_d 分支
git push origin dev_d:dev_d

在 GitLab 等平台创建 PR 合并 dev_d 到 master 分支, 然后让管理员审核

创建PR

本地存在不想提交的临时文件

# 将不想提交的代码 stash 到贮藏区
git stash save "临时配置文件a.yaml"
# 同步远程仓库 master 副本并 merge 到 dev_d 分支
git pull origin master:master
# 推送到远程仓库
git push origin master:maser
# 将暂时贮藏的文件恢复
git stash pop

什么时候会发生代码冲突

Git 有 2 种情况会发生代码冲突

  • 两个人同时修改了同一个文件的同一行 (比如 张三, 李四同时修改了 a.txt 文件的第一行)
  • 修改文件的时候文件名被其他人修改了 (比如 张三修改了 a.txt 文件的第一行, 李四将 a.txt 文件修改为 b.txt(或者删除))

修改了同一个文件的同一行

下面展示一下代码冲突的过程

  • 张三创建 a.txt 并且在第一行写入 1, commit 到本地仓库, push 推送到远程
  • 李四将同步代码后, 将第一行的 1 修改为 2, commit 到本地仓库, push 到远程
  • 张三将第一行修改为 3, commit 到本地, push 到远程
  • 张三代码冲突, 拒绝 push
$ git push
To github.com:dengjiawen8955/git-demo.git
 ! [rejected]        master -> master (non-fast-forward)
error: failed to push some refs to 'git@github.com:dengjiawen8955/git-demo.git'
  • 张三 pull 远程代码, 因为代码冲突, 不能自动 Merge
$ git pull
Auto-merging 0928_2/a.txt
CONFLICT (content): Merge conflict in 0928_2/a.txt
Automatic merge failed; fix conflicts and then commit the result.
  • 张三手动处理冲突, 可以手动编辑冲突的文件或者使用相关可视化工具
# 查看冲突文件
$ git status
On branch master
Your branch and 'origin/master' have diverged,
and have 1 and 1 different commits each, respectively.
  (use "git pull" to merge the remote branch into yours)

You have unmerged paths.
  (fix conflicts and run "git commit")
  (use "git merge --abort" to abort the merge)

Unmerged paths:
  (use "git add <file>..." to mark resolution)
        both modified:   a.txt

no changes added to commit (use "git add" and/or "git commit -a")
# 处理冲突 (注意, 代码覆盖事故就是在这里发生, 冲突处理覆盖了李四的代码)
$ vim a.txt
# 将处理完的文件添加到暂存区
$ git add a.txt
# 提交到本地仓库
$ git commit -m "处理冲突"
# 推送到远程
$ git push

如果本来 李四提交的代码 2 和 张三提交的代码 3 都应该保留的, 张三却没有保留李四的代码, 那么就会发生代码覆盖事故

正确的结果

2
3

张三合并后的结果

3

修改文件的时候文件名被其他人修改了

原理是类似的, 这里不做赘述了

如何减少失误?

  1. 了解 Git 的工作原理和基本命令, 知其然知其所以然, 就能减少失误

  2. 及时提交代码, 更新代码, 避免因为长时间没有同步代码产生过多的冲突文件, 因为在解决冲突的时候初级人员是非常容易出错的

  3. 熟悉 Git 工具, 比如命令行或 GitTortoise, 避免因为工具不熟悉导致失误

  4. 本地修改前应该尽可能的避免本地库与远程之间有过多的差异, 本地修改前执行一次 git pull 先把远程更新拉到本地

  5. pull 之前如果有没有提交的文件, 先 stash

    git stash
    git pull
    git stash pop
    如果有冲突解决冲突
    

出现了代码冲突事故应该怎么做?

如果事故已经发生了, 首先应该查看日志分析原因, 找到出问题的节点撤销操作, 回滚代码

查看日志分析原因

使用命令行或者你熟悉的工具查看分支历史

命令行

#log  --graph 结合使用时尤其有用,这个选项添加了一些ASCII字符串来形象地展示你的分支、合并历史 
$ git log --pretty=format:"%h %s" --graph
*   f3b92cb 解决冲突
|\  
| * 3543686 a.txt第一行修改为3
* | 251b3cb a.txt第一行修改为2
|/  
* 6a432b2 a.txt第一行新增1
# 使用 git diff 查看修改历史 (找出出问题的节点)
$ git diff f3b92cb 3543686

使用其他工具可以更加方便的可视化查看, 这里不赘述了

找到出问题的节点撤销操作

参考: https://blog.csdn.net/jarvan5/article/details/114028765

总结

如果今天的内容你只能记住一件事, 那请记住: 熟悉 Git 工具, 比如命令行或 IDE, 避免因为工具不熟悉导致失误

reference

https://blog.csdn.net/qq_27384769/article/details/80421279

https://git-scm.com/docs


http://lihuaxi.xjx100.cn/news/49767.html

相关文章

[HJ60 查找组成一个偶数最接近的两个素数]

描述 任意一个偶数&#xff08;大于2&#xff09;都可以由2个素数组成&#xff0c;组成偶数的2个素数有很多种情况&#xff0c;本题目要求输出组成指定偶数的两个素数差值最小的素数对。 数据范围&#xff1a;输入的数据满足 4≤n≤1000 输入描述&#xff1a; 输入一个大于…

Python 全栈系列190 全栈能力组建进展梳理

说明 从数据处理的应用角度,梳理一下目前全栈能力的情况。 内容 简单的分为四部分: 1 存储2 处理3 (调度)机制4 监控/管理1 存储【保持使用】 这部分我觉得已经ok了 ⋆ ⋆ ⋆ ⋆ ⋆ \star\star\star\star\star ⋆⋆⋆

led点阵屏静态图

话不多说&#xff0c;上代码&#xff0c;前提是你已经知道各行代码的意思。跟着老师的代码走最好&#xff0c;每一行都一样&#xff0c;要不然会有意想不到的错误&#xff0c;小白阶段就不要自己创新代码了。X﹏X #include <REGX52.H> sbit RCKP3^5; //RCLK sbit SCKP3^6…

C# 多线程二:Interlocked 互锁的理解和简单示例

一.多线程的线程安全 多线程安全问题原因是在cpu执行多线程时&#xff0c;在执行的过程中可能随时切换到其他的线程上执行&#xff0c;当多个线程同时操作同一个变量时&#xff0c;如果不施加其他措施&#xff0c;可能导致错误数据的出现 二.Interlocked的特点 Interlocked是…

JavaWeb - 15 异步请求 Ajax axios

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录1.同步请求与异步请求1.1 同步请求1.2 异步请求2. Ajax发送异步请求2.1 Ajax概述2.2 原生JS实现AJAX详解2.3 代码码演示3. axios框架3.1 axios概述3.2 安装方式3.3 快…

【Linux从0到1】第十七篇:高级IO

文章目录一、五种IO模型二、高级IO重要概念2.1 同步通信 vs 异步通信(synchronous communication/ asynchronouscommunication)2.2 阻塞 vs 非阻塞2.3 其他高级IO2.4 非阻塞IO2.5 I/O多路转接之select2.6 I/O多路转接之poll [选学]2.7 I/O多路转接之epoll一、五种IO模型 阻塞IO…

SpringMVC处理Ajax请求及处理和响应json格式的数据

在SpringMVC中处理Ajax的请求可以用到RequestBody与ResponseBody注解实现 1.RequestBody:将请求体中的内容和控制器方法的形参进行绑定 2.使用RequestBody注解将json格式的请求参数转换程Java对象&#xff08;三个步骤&#xff09; a>导入Jackson的依赖 b>在SpringMVC的…

Redis从入门到精通(一)

Redis 一、Redis安装和概述 1.1、概述 Redis是什么&#xff1f; Redis&#xff08;Remote Dictionary Server )&#xff0c;即远程字典服务&#xff0c; Redis是一个开源的key-value存储系统&#xff0c;当下最热门的NoSQL 技术之一。 1.2、安装 1.把redis-6.2.6.tar.gz上…