Class: Pindo::BuildHelper

Inherits:
Object
  • Object
show all
Includes:
Singleton
Defined in:
lib/pindo/module/build/build_helper.rb

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.share_instanceObject



12
13
14
# File 'lib/pindo/module/build/build_helper.rb', line 12

def share_instance
  instance
end

Instance Method Details

#android_project?(project_path) ⇒ Boolean



70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
# File 'lib/pindo/module/build/build_helper.rb', line 70

def android_project?(project_path)
  # 检查Android工程的关键文件和目录
  gradle_file = File.exist?(File.join(project_path, "build.gradle")) || File.exist?(File.join(project_path, "build.gradle.kts"))
  settings_gradle = File.exist?(File.join(project_path, "settings.gradle")) || File.exist?(File.join(project_path, "settings.gradle.kts"))

  # 尝试获取主模块
  main_module = nil
  begin
    main_module = get_main_module(project_path)
  rescue => e
    puts "获取主模块失败: #{e.message}" if ENV['DEBUG']
  end

  # Android Studio项目结构
  if gradle_file && settings_gradle && main_module
    app_gradle = File.exist?(File.join(main_module, "build.gradle")) || File.exist?(File.join(main_module, "build.gradle.kts"))
    app_manifest = File.exist?(File.join(main_module, "src", "main", "AndroidManifest.xml"))
    return true if app_gradle && app_manifest
  end

  # 如果无法通过标准方式检测,尝试更宽松的检测
  # 检查是否有任何包含 build.gradle 的子目录
  if gradle_file && settings_gradle
    Dir.entries(project_path).each do |entry|
      next if entry.start_with?('.')
      entry_path = File.join(project_path, entry)
      if File.directory?(entry_path)
        app_gradle = File.exist?(File.join(entry_path, "build.gradle")) || File.exist?(File.join(entry_path, "build.gradle.kts"))
        app_manifest = File.exist?(File.join(entry_path, "src", "main", "AndroidManifest.xml"))
        if app_gradle && app_manifest
          return true
        end
      end
    end
  end

  false
end

#get_project_name(project_path) ⇒ Object



132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
# File 'lib/pindo/module/build/build_helper.rb', line 132

def get_project_name(project_path)
  case project_type(project_path)
  when :unity
    File.basename(project_path)
  when :ios
    xcodeproj = Dir.glob(File.join(project_path, "*.xcodeproj")).first
    File.basename(xcodeproj, ".xcodeproj") if xcodeproj
  when :android
    settings_gradle = File.join(project_path, "settings.gradle")
    settings_gradle_kts = File.join(project_path, "settings.gradle.kts")
    
    # 优先使用 settings.gradle.kts,如果不存在则使用 settings.gradle
    if File.exist?(settings_gradle_kts)
      settings_gradle = settings_gradle_kts
    end
    
    if File.exist?(settings_gradle)
      content = File.read(settings_gradle)
      if content =~ /rootProject\.name\s*=\s*['"](.+)['"]/
        $1
      else
        File.basename(project_path)
      end
    else
      File.basename(project_path)
    end
  else
    File.basename(project_path)
  end
end

#get_project_version(project_path) ⇒ Object



163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
# File 'lib/pindo/module/build/build_helper.rb', line 163

def get_project_version(project_path)
  case project_type(project_path)
  when :unity
    version_file = File.join(project_path, "ProjectSettings", "ProjectVersion.txt")
    if File.exist?(version_file)
      content = File.read(version_file)
      if content =~ /m_EditorVersion: (.*)/
        $1.strip
      end
    end
  when :ios
    # 从Info.plist获取版本号
    nil
  when :android
    # 从build.gradle获取版本号
    nil
  end
end

#ios_project?(project_path) ⇒ Boolean



30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
# File 'lib/pindo/module/build/build_helper.rb', line 30

def ios_project?(project_path)
  # 检查iOS工程的关键文件
  xcodeproj_files = Dir.glob(File.join(project_path, "*.xcodeproj"))
  workspace_files = Dir.glob(File.join(project_path, "*.xcworkspace"))

  # 至少要有.xcodeproj文件或.xcworkspace文件
  return false if xcodeproj_files.empty? && workspace_files.empty?

  if !xcodeproj_files.empty?
    # 检查.xcodeproj内部结构
    project_file = File.join(xcodeproj_files.first, "project.pbxproj")
    return true if File.exist?(project_file)
  end

  if !workspace_files.empty?
    # 检查.xcworkspace内部结构
    contents_file = File.join(workspace_files.first, "contents.xcworkspacedata")
    return true if File.exist?(contents_file)
  end

  false
end

#load_jps_build_config(project_dir) ⇒ String?

加载 JPSBuildConfig.json 并设置项目名称到 GlobalOptionsState



197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
# File 'lib/pindo/module/build/build_helper.rb', line 197

def load_jps_build_config(project_dir)
  # 检测工程类型:Unity 工程配置在 ProjectSettings 目录
  config_file = if unity_project?(project_dir)
    File.join(project_dir, 'ProjectSettings', 'JPSBuildConfig.json')
  else
    File.join(project_dir, 'JPSBuildConfig.json')
  end

  return nil unless File.exist?(config_file)

  begin
    config = JSON.parse(File.read(config_file))
    project_name = config['project_name']
    if project_name && !project_name.empty?
      # 设置到 GlobalOptionsState
      Pindo::Options::GlobalOptionsState.instance[:proj] = project_name
      puts "使用 JPS 配置的项目名称: #{project_name}"
      return project_name
    end
  rescue => e
    puts "加载 JPSBuildConfig.json 失败: #{e.message}" if ENV['PINDO_VERBOSE'] == '1'
  end
  nil
end

#macos_project?(project_path) ⇒ Boolean



53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
# File 'lib/pindo/module/build/build_helper.rb', line 53

def macos_project?(project_path)
  # 检查是否为 macOS 工程
  begin
    project_fullname = Dir.glob(File.join(project_path, "*.xcodeproj")).max_by {|f| File.mtime(f)}
    if !project_fullname.nil?
      project_obj = Xcodeproj::Project.open(project_fullname)
      project_build_platform = project_obj.root_object.build_configuration_list.get_setting("SDKROOT")["Release"]
      if !project_build_platform.nil? && project_build_platform.eql?("macosx")
        return true
      end
    end
  rescue => e
    puts "判断 macOS 工程失败: #{e.message}" if ENV['DEBUG']
  end
  false
end

#project_type(project_path) ⇒ Object

Raises:

  • (ArgumentError)


109
110
111
112
113
114
115
116
117
# File 'lib/pindo/module/build/build_helper.rb', line 109

def project_type(project_path)
  raise ArgumentError, "项目路径不能为空" if project_path.nil? || project_path.empty?
  raise ArgumentError, "项目路径不存在: #{project_path}" unless File.directory?(project_path)

  return :unity if unity_project?(project_path)
  return :ios if ios_project?(project_path)
  return :android if android_project?(project_path)
  :unknown
end

#project_type_name(project_path) ⇒ Object



119
120
121
122
123
124
125
126
127
128
129
130
# File 'lib/pindo/module/build/build_helper.rb', line 119

def project_type_name(project_path)
  case project_type(project_path)
  when :unity
    "Unity"
  when :ios
    "iOS"
  when :android
    "Android"
  else
    "Unknown"
  end
end

#pull_appconfig_with_reponame(repo_name:, target_dir: nil) ⇒ Boolean

拉取应用配置仓库(委托给 BuildInfoManager)



186
187
188
189
190
191
192
# File 'lib/pindo/module/build/build_helper.rb', line 186

def pull_appconfig_with_reponame(repo_name:, target_dir: nil)
  require_relative '../../config/build_info_manager'
  Pindo::BuildInfoManager.share_instance.pull_appconfig_with_reponame(
    repo_name: repo_name,
    target_dir: target_dir
  )
end

#unity_project?(project_path) ⇒ Boolean



17
18
19
20
21
22
23
24
25
26
27
28
# File 'lib/pindo/module/build/build_helper.rb', line 17

def unity_project?(project_path)
  # 检查Unity工程的关键文件和目录
  project_settings_path = File.join(project_path, "ProjectSettings")
  assets_path = File.join(project_path, "Assets")
  packages_path = File.join(project_path, "Packages")

  # Unity工程必须包含这些目录和文件
  File.directory?(project_settings_path) &&
  File.directory?(assets_path) &&
  File.directory?(packages_path) &&
  File.exist?(File.join(project_settings_path, "ProjectSettings.asset"))
end