当前位置: 首页 > news >正文

repo的patch转换成git am能打的patch

安卓sdk项目小的几十G,大的上百G,有的人会把sdk分成许多个小的git然后统一用repo来管理,还有的人会选择把sdk放在一个git中管理. 那么repo中修改后生成的patch是无法直接给git用的,因为路径不一样,patch内容也不相符
比如repo中device子目录是一个git,那么它生成的patch放到另一个git项目中只能cd到device路径,然后再用patch指令打,无法用git am xx.patch来打. 两边同步代码会很麻烦.
需要用脚本进行一个转换.

repo生成manifest快照

repo比如要生成0801到0805之间的修改的patch
8月1号用如下指令生成快照
./repo sync
./repo manifest -r -o manifest_0801.xml

中间做过修改.

8月5号再生成快照
./repo sync
./repo manifest -r -o manifest_0805.xml
得有两个快照, 才能生成这两个快照之间的diff提交.
生成快照后,接下来用脚本来生成两个快照间的修改的patch

生成repo快照间的提交的patch并转换成git am的patch

# 作者帅得不敢出门
# -*- coding: utf-8 -*-import sys
import os
import re
import subprocessdef do_popen(cmd):#popenprocess = subprocess.Popen(cmd, stdout=subprocess.PIPE, stdin=subprocess.PIPE, shell=True)stdout, stderr = process.communicate()return stdout.decode('utf-8')def auto_detect_manifests():"""遍历repo项目根目录,找到两个快照,快照以.xml结尾"""manifests = []for item in os.listdir('./'):if item.startswith('manifest') and item.endswith('.xml'):manifests.append(item)if len(manifests) != 2:print('Error:the number of manifest_xx.xml files are not equal to 2, abort!')sys.exit(1)manifests.sort()print(manifests)return manifestsdef get_diffmanifests():"""查看两个repo快照间的差异, 得到类似如下changed projects :bootable/bootloader/lk changed from e5f360f35a6d3848475ba4920f40c1609b1348b0 to ca0100b2da6ca7831348cb5fcfe8d23c529e8a57[+] ca0100b2 edit 1device/sprd/sepolicy changed from f15d0189283f767bd315f0900a59256323c071c2 to 64c586a362cb19a290280e79b2e20e8aab7d94cc[+] 64c586a hellokernel/msm-3.18 changed from f36f37a42a94fe78d5d7cbe2e8a4ab6477de74ab to 6b372c76fc0874d19822d978ad557a4aeec0ebee[+] 6b372c76fc08 word"""manifests = auto_detect_manifests()cmd = './repo diffmanifests ' + manifests[0] + ' ' + manifests[1]print(cmd)return do_popen(cmd)def get_diff_git_log():"""得到两个repo快照间的git修改的log[{'path': 'bootable/bootloader/lk', 'from': 'e5f360f35a6d3848475ba4920f40c1609b1348b0', 'to': 'ca0100b2da6ca7831348cb5fcfe8d23c529e8a57'}, {'path': 'device/sprd/sepolicy', 'from': 'f15d0189283f767bd315f0900a59256323c071c2', 'to': '64c586a362cb19a290280e79b2e20e8aab7d94cc'}, {'path': 'kernel/msm-3.18', 'from': 'f36f37a42a94fe78d5d7cbe2e8a4ab6477de74ab', 'to': '6b372c76fc0874d19822d978ad557a4aeec0ebee'}]"""data = get_diffmanifests()print(data)# 只保留\t开头的有效行line = [ x for x in data.split('\n') if x.startswith('\t')]ret = []for i in range(len(line)):if i % 2 == 0:#print(line[i])log = line[i].split()ret.append({'path':log[0], 'from':log[3], 'to':log[5]})#print(ret)return retdef get_format_patch(log, outdir):try:do_popen('rm ./*.patch ')except Exception as e:print('')# 生成从from开始的提交的git patch,生成的git是在子目录中生成的,所以需要在patch内容中的文件路径添加父目录do_popen('git format-patch ' + log['from'])for file in os.listdir('./'):if file.endswith('.patch'):print(file)with open(file, 'r') as fp:new_lines = []lines = fp.readlines()fp.close()for line in lines:#查找文件路径,并在前面拼接上目录, 把repo补丁转换成可以直接在git上打的patchif line.startswith('diff --git') or line.startswith('--- ') or line.startswith('+++ '):#print(line)new_line = re.sub(' a/', ' a/' + log['path'] + '/', line)new_line = re.sub(' b/', ' b/' + log['path'] + '/', new_line)#print(new_line)new_lines.append(new_line)else:new_lines.append(line)patch_name = os.path.join(outdir, file)with open(patch_name, 'w') as new_fp:print(patch_name)new_fp.writelines(new_lines)new_fp.close()try:do_popen('rm ./*.patch ')except Exception as e:print('')if __name__ == '__main__':"""通过repo获取到两个时间段的提交git log, 再通过git log获取patch"""# 生成的patch放在当前目录的patchs中patch_dir = os.path.join(os.getcwd(), 'patchs')if not os.path.exists(patch_dir):os.mkdir(patch_dir)else:try:# 先删除旧的patchdo_popen('rm ' + patch_dir + './*.patch ')except Exception as e:print('')#得到两个repo快照间的git修改的loglogs = get_diff_git_log()for log in logs:# 遍历git log进入到实际的子git目录中生成patchold_dir = os.getcwd()os.chdir(log['path'])print(log['path'])# 把所有的子git中的修改制作成patch放到patchs目录下get_format_patch(log, patch_dir)os.chdir(old_dir)

作者:帅得不敢出门 csdn原创谢绝转载

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • 三级_网络技术_43_综合题(报文)
  • USB设备驱动代码分析(鼠标)
  • 如何设置PowerBI报告展示在屏幕的大小?
  • 【AI赋能游戏】《黑神话:悟空》专属黑悟空无限创意生成器!(整合包分享)
  • 选择排序(直接选择排序和堆排序)
  • Go Convey测试框架入门(go convey gomonkey)
  • 特殊类设计和类型转换
  • 进阶SpringBoot之 SpringSecurity(2)用户认证和授权
  • TIM输出比较之PWM驱动直流电机应用案例
  • UEFI启动流程
  • 《黑神话:悟空》到底是用什么语言开发的
  • 从0到1构建视频汇聚生态:EasyCVR视频汇聚平台流媒体协议支持的前瞻性布局
  • 依靠 VPN 生存——探索 VPN 后利用技术
  • 【Python】列表和元组
  • 两个独立的SpringBoot项目如何互相引用?
  • Bytom交易说明(账户管理模式)
  • Hibernate最全面试题
  • java多线程
  • Meteor的表单提交:Form
  • mysql 5.6 原生Online DDL解析
  • Redis 中的布隆过滤器
  • spark本地环境的搭建到运行第一个spark程序
  • spring cloud gateway 源码解析(4)跨域问题处理
  • windows下如何用phpstorm同步测试服务器
  • 百度地图API标注+时间轴组件
  • 程序员最讨厌的9句话,你可有补充?
  • 飞驰在Mesos的涡轮引擎上
  • 机器学习学习笔记一
  • 机器学习中为什么要做归一化normalization
  • 看域名解析域名安全对SEO的影响
  • 猫头鹰的深夜翻译:Java 2D Graphics, 简单的仿射变换
  • 免费小说阅读小程序
  • 浅谈web中前端模板引擎的使用
  • 全栈开发——Linux
  • 浅谈sql中的in与not in,exists与not exists的区别
  • ​sqlite3 --- SQLite 数据库 DB-API 2.0 接口模块​
  • #[Composer学习笔记]Part1:安装composer并通过composer创建一个项目
  • $(this) 和 this 关键字在 jQuery 中有何不同?
  • (2020)Java后端开发----(面试题和笔试题)
  • (8)Linux使用C语言读取proc/stat等cpu使用数据
  • (k8s)Kubernetes 从0到1容器编排之旅
  • (二)fiber的基本认识
  • (附源码)ssm高校实验室 毕业设计 800008
  • (三)SvelteKit教程:layout 文件
  • (四)汇编语言——简单程序
  • (图)IntelliTrace Tools 跟踪云端程序
  • ***汇编语言 实验16 编写包含多个功能子程序的中断例程
  • .mysql secret在哪_MYSQL基本操作(上)
  • .net 桌面开发 运行一阵子就自动关闭_聊城旋转门家用价格大约是多少,全自动旋转门,期待合作...
  • .net6Api后台+uniapp导出Excel
  • .net之微信企业号开发(一) 所使用的环境与工具以及准备工作
  • .net专家(高海东的专栏)
  • .one4-V-XXXXXXXX勒索病毒数据怎么处理|数据解密恢复
  • [ CTF ] WriteUp- 2022年第三届“网鼎杯”网络安全大赛(白虎组)
  • [2009][note]构成理想导体超材料的有源THz欺骗表面等离子激元开关——