iOS主工程修改后一键同步Pod的ruby脚本(进阶一)

2,177 阅读1分钟

Example是壳工程,当需求涉及到多个模块的修改时,为了方便提交各个Pod的代码,写了个ruby脚本

  • 规则1:目录结构如下
  • 规则2:提交日志以PodSync:开头
  • 修改下work_path的取值,脚本就可以配置在持续集成服务器上。
  • TODO1:执行状态通知,因为各个Pod同步后commit就变了,壳工程应该pod update
  • TODO2:利用Gitlab Api 直接提交代码,就不用clone了
├── Podfile  
├── Podfile.lock  
├── Pods  
│   ├── ABCPods1  
│   │   └── Code1.m  
│   ├── ABCPods2  
│   │   └── Code2.m  
│   ├── ABCPods3  
│   │   └── Code3.m  
│   ├── Headers  
│   ├── Local Podspecs  
│   ├── Manifest.lock  
│   ├── Pods.xcodeproj  
│   └── Target Support Files  
├── Example  
│   ├── AppDelegate.h  
│   └── AppDelegate.m  
├── Example.xcodeproj  
└── Example.xcworkspace  

ABCPods都是用pod lib create 创建的,目录结构一致 ,ABCPods下有同名ABCPods下是模块代码,类似:

├── ABCPods1  
│   ├── ABCPods1  
│   │   └── Code1.m  

自动同步的ruby脚本如下:

# frozen_string_literal: true

require 'pathname'
require 'git'
require 'fileutils'

work_path = Pathname.new '.../path/to/Example'

url_config = { 'ABCPods1' => 'http://example.com/ios_code/ABCPods1.git',
               'ABCPods2' => 'http://example.com/ios_code/ABCPods2.git',
               'ABCPods3' => 'http://example.com/ios_code/ABCPods3.git' }
               
Git.configure do |config|
  config.binary_path = '/usr/local/bin/git'
end



g = Git.open work_path
current_branch = g.current_branch
puts "current_branch:#{current_branch}"
commits = g.log(2) # 获取最新两次提交
first_commit = commits.first
last_commit = commits.last
puts "本次提交id: #{first_commit}"
puts first_commit.message
puts "上次提交id: #{last_commit}"
# 提交日志约定以 PodSync: 开头
unless first_commit.message.include? 'PodSync:'
  puts '提交日志没有 PodSync: 开头'
  exit 0
end

if first_commit.parents.size > 1
  puts '这是一个合并提交,不能同步合并提交'
  exit 1
end

file_list = g.diff(first_commit, commits.last).name_status.map(&:first)

# 需要排除一些文件 Local Podspecs Manifest.lock Headers 等
pod_file_list = file_list.select do |e|
  next if e.end_with? 'Manifest.lock'
  next if e.start_with? 'Pods/Local Podspecs'
  next if e.start_with? 'Pods/Target Support Files'
  next if e.start_with? 'Pods/Headers'

  e.start_with? 'Pods/'
end
puts "pod_file_list#{pod_file_list}"
# 转换成Pod名
pod_file_list_map = pod_file_list.map { |e| e.split('/')[1] }
# 去掉重复的,得到修改的Pod数组
pod_file_list_set = pod_file_list_map.uniq
puts pod_file_list_set

Dir.mktmpdir do |dir|
  pod_file_list_set.each do |item|
    begin
      puts "Clone: #{url_config[item]}, dir #{item}, branch : #{current_branch}"
      g = Git.clone(url_config[item], item, path: dir, branch: current_branch)
    rescue StandardError => e
      puts e
      exit 1
    end

    src = work_path + 'Pods' + item + item
    dest = Pathname.new(dir) + item + item

    puts "#{src} copy to #{dest}"
    FileUtils.rm_r(dest, force: true)

    FileUtils.cp_r(src, dest.parent)
    # puts g.status.changed 状态貌似有缓存 还是命令行准确
    status_output = `git -C #{dest.parent} status`
    puts status_output unless status_output.include? 'working tree clean'
    # 提交&推送
    `git -C #{dest.parent} commit -a -m 'Over PodSync'`
    `git -C #{dest.parent} push`
  end
end