pindo 5.20.5 → 5.20.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: e05f84df2bd17ab7420a8975c8a6811f24080b11a4080391aff016f6f010b18f
4
- data.tar.gz: 16c2db8376e2ec3e3f38ef5e0bd45eddaffb8434c65df25a95c27cdd265db469
3
+ metadata.gz: c0edb06546cd16285c138448253905ee5649e4e171af1a13cfbb61942f169e03
4
+ data.tar.gz: 88760601ffcc0a1863d537a8e1bf5a7f26f7ddb840b96831825e3699a26d2f5c
5
5
  SHA512:
6
- metadata.gz: 14c3dd4dad433a639f118211ff83a2aed05b9ce63155c45c9f3293c1f52a6b39d1161ca1b1b175f1104fd51af54466e17d36c39c5fbafed8e6bfa0783827d143
7
- data.tar.gz: d3675cbbfb84617cf00c13284c7450d69b4edf7bea3159c477d45cdb4db4327515bb50fba9c3b2fa4d31a9513f6222661f3652b9193350acfb959ada39bc9e5c
6
+ metadata.gz: c35bf1529656b6a5a24a2e727db177943ce3ab78a3fcc837a985b4584a62e1512897430e6520c4eaf146bc2a7b3c8ba6fca8d9e1af270826b31f0a070f81a8da
7
+ data.tar.gz: 4a9ecf6b0f98d988ca930c660d7082f0fe266698934926238482577cef0cd4c1f594ef686532a61aafa7a3cbb046aead11fa776da7a444344362b881d6d0e607
@@ -1125,10 +1125,11 @@ module Pindo
1125
1125
  # @param git_commit_id [String] Git commit SHA
1126
1126
  # @param workflow_id [Integer] 工作流ID(可选)
1127
1127
  # @return [Hash, nil] commit_log 记录或 nil
1128
- def find_commit_log_by_git_commit_id(git_commit_id, workflow_id = nil)
1128
+ def find_commit_log_by_git_commit_id(git_commit_id, workflow_id = nil, branch = nil)
1129
1129
  params = {
1130
1130
  pageNo: 1,
1131
- pageSize: 50 # 查询最近的 50 条记录
1131
+ pageSize: 50, # 查询最近的 50 条记录
1132
+ onlyCliff: false
1132
1133
  }
1133
1134
 
1134
1135
  # 如果指定了 workflow_id,添加到筛选条件
@@ -1140,26 +1141,16 @@ module Pindo
1140
1141
  if list_result && list_result["data"] && list_result["data"]["details"]
1141
1142
  details = list_result["data"]["details"]
1142
1143
 
1143
- # 遍历查找匹配的 commitId
1144
- # 支持完整匹配或前缀匹配(git SHA)
1145
- commit_log = details.find do |item|
1146
- item_commit_id = item["commitId"]
1147
- next false unless item_commit_id
1148
-
1149
- # 完整匹配
1150
- if item_commit_id == git_commit_id
1151
- true
1152
- # 前缀匹配(支持 git 短 SHA,如 9e959ffd)
1153
- elsif git_commit_id.length >= 7 && item_commit_id.start_with?(git_commit_id)
1154
- true
1155
- elsif git_commit_id.length >= 7 && git_commit_id.start_with?(item_commit_id)
1156
- true
1157
- else
1158
- false
1159
- end
1144
+ matched_logs = details.select { |item| same_commit?(item["commitId"], git_commit_id) }
1145
+ return nil if matched_logs.empty?
1146
+
1147
+ if !branch.nil?
1148
+ branch_text = branch.to_s
1149
+ branch_matched = matched_logs.find { |item| item["branch"].to_s == branch_text }
1150
+ return branch_matched if branch_matched
1160
1151
  end
1161
1152
 
1162
- return commit_log
1153
+ return matched_logs.first
1163
1154
  end
1164
1155
  rescue => e
1165
1156
  Funlog.instance.warning("查询 commit_log 列表失败: #{e.message}")
@@ -1168,6 +1159,30 @@ module Pindo
1168
1159
  nil
1169
1160
  end
1170
1161
 
1162
+ # 从 commit_log 记录中提取发送消息需要的 indexNo。
1163
+ #
1164
+ # commit_log/list 的真实响应里 indexNo 不在根节点,而在 bindVersions 的各平台包里。
1165
+ # 同一 commit 可能绑定多个平台,send_message 实测使用其中一个包的 indexNo;
1166
+ # 取最大值可匹配当前线上请求数据,并稳定指向最近生成的包序号。
1167
+ #
1168
+ # @param commit_log [Hash, nil] commit_log/list 的单条记录
1169
+ # @return [Integer, nil] indexNo
1170
+ def commit_log_message_index_no(commit_log)
1171
+ return nil unless commit_log.is_a?(Hash)
1172
+
1173
+ root_index_no = commit_log["indexNo"]
1174
+ return root_index_no if root_index_no
1175
+
1176
+ bind_versions = commit_log["bindVersions"]
1177
+ return nil unless bind_versions.is_a?(Hash)
1178
+
1179
+ bind_versions.values.map do |version_info|
1180
+ next nil unless version_info.is_a?(Hash)
1181
+
1182
+ version_info["indexNo"]
1183
+ end.compact.max
1184
+ end
1185
+
1171
1186
  def get_user_local_wechat_url( )
1172
1187
 
1173
1188
  wechat_msg_url = nil
@@ -1799,24 +1814,21 @@ module Pindo
1799
1814
 
1800
1815
  # 获取特定 commit 已绑定的包 ID
1801
1816
  #
1802
- # 数据源是 commit_log/preview 的 bindVersions。
1817
+ # 数据源是 commit_log/list 的 bindVersions。
1803
1818
  #
1804
1819
  # 不能用 project_package/bind_list:它按 projectId 查、作用域看似更宽,
1805
1820
  # 但实测(项目 930 条记录)每条的 commitId、branch、workflowId、commitLogs
1806
1821
  # 全部为 nil——该接口只返回包本身,不携带 commit 绑定关系,
1807
1822
  # 按 commitId 过滤会恒得空列表,进而让覆盖式写入误删该 commit 的已有绑定。
1808
1823
  #
1809
- # preview 需要传 workflowId,但实测同项目下不同 workflowId(3457 / 2650)
1810
- # 返回的 bindVersions 完全一致——绑定按 commitId 全局记录,
1811
- # 不存在"按工作流查漏、覆盖时被删掉"的问题。
1812
- #
1813
1824
  # 绑定接口是覆盖式写入,调用方需要把已绑定的包一起提交,因此必须区分
1814
1825
  # 「确认没有绑定过」和「查不出来」——后者返回空数组会导致已有绑定被静默覆盖丢失。
1815
1826
  #
1816
1827
  # @param commit_id [String] Git commit SHA(必需)
1817
1828
  # @param workflow_id [Integer, String] 工作流 ID(必需,接口入参)
1829
+ # @param excluded_package_types [Array<String>] 要排除的平台类型(本次新包会替换这些旧绑定)
1818
1830
  # @return [Array<String>, nil] 已绑定的包 ID 数组;查询失败或结构异常时返回 nil
1819
- def get_commit_bound_package_ids(commit_id:, workflow_id:)
1831
+ def get_commit_bound_package_ids(commit_id:, workflow_id:, excluded_package_types: [])
1820
1832
  if commit_id.nil? || commit_id.empty?
1821
1833
  Funlog.instance.fancyinfo_warning("commit_id 为空,无法查询已绑定的包")
1822
1834
  return nil
@@ -1828,10 +1840,13 @@ module Pindo
1828
1840
  end
1829
1841
 
1830
1842
  begin
1831
- result = @pgyer_client.get_commit_log_preview(
1832
- workflowId: workflow_id,
1833
- commitIds: [commit_id],
1834
- params: { onlyCliff: false }
1843
+ result = @pgyer_client.get_commit_log_list(
1844
+ params: {
1845
+ workflowIds: [workflow_id],
1846
+ pageNo: 1,
1847
+ pageSize: 50,
1848
+ onlyCliff: false
1849
+ }
1835
1850
  )
1836
1851
 
1837
1852
  # 兼容两种响应格式
@@ -1839,22 +1854,26 @@ module Pindo
1839
1854
 
1840
1855
  unless result && (response_code == 0 || response_code == 200)
1841
1856
  error_msg = result&.dig("msg") || result&.dig("meta", "message") || "未知错误"
1842
- Funlog.instance.fancyinfo_warning("查询 Commit #{commit_id[0..7]} 的绑定信息失败: #{error_msg}")
1857
+ Funlog.instance.fancyinfo_warning("查询 Commit #{commit_id[0..7]} 的提交记录失败: #{error_msg}")
1843
1858
  return nil
1844
1859
  end
1845
1860
 
1846
- data = result&.dig("data")
1861
+ details = result&.dig("data", "details")
1847
1862
 
1848
- # code=0 且 data=nil 是接口表达「没有这条 commit」的正常响应(实测确认),
1863
+ # code=0 且 details=nil 是接口表达「没有这条 commit」的正常响应(实测确认),
1849
1864
  # 不是畸形响应。此时该 commit 还没进 commit log,不可能有已记录的绑定。
1850
1865
  # 若误判为 nil,首次绑定(commit log 尚未生成)会被整体阻断。
1851
- if data.nil?
1866
+ if details.nil?
1852
1867
  puts "[PINDO_DEBUG] Commit #{commit_id[0..7]} 不在 commit log 中,视为未绑定" if ENV['PINDO_DEBUG']
1853
1868
  return []
1854
1869
  end
1855
1870
 
1856
- list = data.is_a?(Array) ? data : [data]
1857
- matched = list.select { |item| item.is_a?(Hash) && same_commit?(item["commitId"], commit_id) }
1871
+ unless details.is_a?(Array)
1872
+ Funlog.instance.fancyinfo_warning("commit_log/list details 结构异常(#{details.class}),无法确认已有绑定")
1873
+ return nil
1874
+ end
1875
+
1876
+ matched = details.select { |item| item.is_a?(Hash) && same_commit?(item["commitId"], commit_id) }
1858
1877
 
1859
1878
  # 接口正常返回但没有这条 commit:该 commit 还没进 commit log,
1860
1879
  # 也就不可能有已记录的绑定
@@ -1867,8 +1886,14 @@ module Pindo
1867
1886
  # 实测 commit_log/list 可见),哪条带 bindVersions 没有契约保证。
1868
1887
  # 只取第一条匹配会漏读绑定,进而让覆盖式写入删掉已有绑定,
1869
1888
  # 因此合并所有匹配记录的绑定。
1889
+ excluded_types = excluded_package_types.map { |item| normalize_package_type(item) }.compact
1870
1890
  package_ids = []
1871
1891
  matched.each do |commit_info|
1892
+ unless commit_info.key?("bindVersions")
1893
+ Funlog.instance.fancyinfo_warning("commit_log/list 缺少 bindVersions 字段,无法确认已有绑定")
1894
+ return nil
1895
+ end
1896
+
1872
1897
  bind_versions = commit_info["bindVersions"]
1873
1898
 
1874
1899
  # 该记录没有绑定信息:未绑定的 commit 就是 null,属正常情况
@@ -1882,6 +1907,7 @@ module Pindo
1882
1907
  # bindVersions 形如 { "ipa" => { "projectPackageId" => "..." }, ... },
1883
1908
  # 每个平台一个包
1884
1909
  bind_versions.each do |platform, version_info|
1910
+ next if excluded_types.include?(normalize_package_type(platform))
1885
1911
  next if version_info.nil?
1886
1912
 
1887
1913
  unless version_info.is_a?(Hash)
@@ -1910,6 +1936,21 @@ module Pindo
1910
1936
  end
1911
1937
  end
1912
1938
 
1939
+ # 归一化包平台类型,用于比较上传包类型和 bindVersions 平台 key。
1940
+ #
1941
+ # 服务端不同接口可能返回 "ipa"、"IPA" 或 "ipa#packageName" 这类变体。
1942
+ # 绑定接口是覆盖式写入,若同类型旧包没被排除,会出现 ipa 新旧包一起提交,
1943
+ # 最终回读仍是旧 ipa,导致校验缺失新包。
1944
+ #
1945
+ # @param package_type [Object] 平台类型
1946
+ # @return [String, nil] 归一化后的平台类型
1947
+ def normalize_package_type(package_type)
1948
+ value = package_type.to_s.strip.downcase
1949
+ return nil if value.empty?
1950
+
1951
+ value.split('#', 2).first
1952
+ end
1953
+
1913
1954
  # 判断两个 commit SHA 是否指向同一个提交
1914
1955
  #
1915
1956
  # 一端是全长 40 位 SHA、另一端是短 SHA(或大小写不同)时,严格 == 会永不命中。
@@ -2070,8 +2111,7 @@ module Pindo
2070
2111
  # @param project_id [String] 项目 ID
2071
2112
  # @param workflow_id [Integer] 工作流 ID
2072
2113
  # @param commit_id [String] Git commit SHA
2073
- # @param branch [String, nil] 分支名(可选,nil 时不发送分支字段——传错的分支名
2074
- # 会让 commit 与分支错误关联,比不传更糟)
2114
+ # @param branch [String, nil] 分支名(可选,空值时按接口真实参数传空字符串)
2075
2115
  # @param single [Boolean] 是否单个提交(可选,默认 true)
2076
2116
  # @return [Hash] 发送结果
2077
2117
  def send_workflow_message(project_id:, workflow_id:, commit_id:, branch: nil, single: true)
@@ -2091,15 +2131,22 @@ module Pindo
2091
2131
  end
2092
2132
 
2093
2133
  begin
2134
+ commit_log = find_commit_log_by_git_commit_id(commit_id, workflow_id, branch)
2135
+ commit_log_id = commit_log && commit_log["id"]
2136
+ index_no = commit_log_message_index_no(commit_log)
2137
+
2138
+ body_params = {
2139
+ single: single,
2140
+ ids: commit_log_id ? [commit_log_id] : nil,
2141
+ commitIds: [commit_id],
2142
+ branch: branch.to_s,
2143
+ indexNo: index_no
2144
+ }.compact
2145
+
2094
2146
  result = @pgyer_client.send_commit_log_message(
2095
2147
  projectId: project_id,
2096
2148
  workflowId: workflow_id,
2097
- params: {
2098
- single: single,
2099
- # jpsclient 内部归一化为服务端要求的 branches 数组;nil 时不带该字段
2100
- branch: branch,
2101
- commitIds: [commit_id]
2102
- }.compact
2149
+ params: body_params
2103
2150
  )
2104
2151
 
2105
2152
  # 兼容两种响应格式
@@ -118,6 +118,7 @@ module Pindo
118
118
  if project_package_ids.empty?
119
119
  raise "app_version_list 中的包都缺少 id 字段"
120
120
  end
121
+ package_types = @app_version_list.map { |pkg| package_type_from(pkg) }.compact.uniq
121
122
 
122
123
  # 4. 打印绑定信息
123
124
  puts ""
@@ -125,7 +126,7 @@ module Pindo
125
126
  puts " Git Commit: #{@git_commit_id[0..7]}"
126
127
  puts " 包数量: #{project_package_ids.size} 个"
127
128
  @app_version_list.each do |pkg|
128
- package_type = pkg['nativePackageType'] || pkg['originalType'] || 'unknown'
129
+ package_type = raw_package_type_from(pkg) || 'unknown'
129
130
  puts " [#{package_type}] ID: #{pkg['id']}, Version: #{pkg['projectVersion']}, Build: #{pkg['build']}"
130
131
  end
131
132
  if @git_commit_desc
@@ -153,7 +154,8 @@ module Pindo
153
154
  # 7. 获取当前 commit 已绑定的包 ID
154
155
  existing_bound_ids = pgyer_helper.get_commit_bound_package_ids(
155
156
  commit_id: @git_commit_id,
156
- workflow_id: workflow_id
157
+ workflow_id: workflow_id,
158
+ excluded_package_types: package_types
157
159
  )
158
160
 
159
161
  # 查询失败(nil)时中止:绑定接口是覆盖式写入,带着不完整的列表提交
@@ -166,8 +168,8 @@ module Pindo
166
168
  puts " 📋 当前 Commit 已绑定的包: #{existing_bound_ids.size} 个"
167
169
  end
168
170
 
169
- # 8. 合并当前 commit 已绑定的 ID 和新上传的包 ID(去重)
170
- merged_package_ids = (existing_bound_ids + project_package_ids).uniq
171
+ # 8. 合并新上传的包 ID 和其它平台已绑定的 ID(同平台旧包已在查询时排除)
172
+ merged_package_ids = (project_package_ids + existing_bound_ids).uniq
171
173
 
172
174
  puts " 📦 合并后的包 ID 数量: #{merged_package_ids.size} 个"
173
175
  if merged_package_ids.size > project_package_ids.size
@@ -221,6 +223,28 @@ module Pindo
221
223
 
222
224
  private
223
225
 
226
+ def package_type_from(pkg)
227
+ normalize_package_type(raw_package_type_from(pkg))
228
+ end
229
+
230
+ def raw_package_type_from(pkg)
231
+ return nil unless pkg.respond_to?(:[])
232
+
233
+ pkg['nativePackageType'] || pkg[:nativePackageType] ||
234
+ pkg['originalType'] || pkg[:originalType] ||
235
+ pkg['packageType'] || pkg[:packageType] ||
236
+ pkg['native_package_type'] || pkg[:native_package_type] ||
237
+ pkg['original_type'] || pkg[:original_type] ||
238
+ pkg['type'] || pkg[:type]
239
+ end
240
+
241
+ def normalize_package_type(package_type)
242
+ value = package_type.to_s.strip.downcase
243
+ return nil if value.empty?
244
+
245
+ value.split('#', 2).first
246
+ end
247
+
224
248
  # 写后回读校验:确认期望绑定的包都在服务端的绑定列表里
225
249
  #
226
250
  # 查询失败时只告警不失败——包已经写进去了,回读失败不代表绑定失败。
data/lib/pindo/version.rb CHANGED
@@ -6,7 +6,7 @@ require 'time'
6
6
 
7
7
  module Pindo
8
8
 
9
- VERSION = "5.20.5"
9
+ VERSION = "5.20.6"
10
10
 
11
11
  class VersionCheck
12
12
  RUBYGEMS_API = 'https://rubygems.org/api/v1/gems/pindo.json'
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pindo
3
3
  version: !ruby/object:Gem::Version
4
- version: 5.20.5
4
+ version: 5.20.6
5
5
  platform: ruby
6
6
  authors:
7
7
  - wade
@@ -112,7 +112,7 @@ dependencies:
112
112
  version: '2.7'
113
113
  - - ">="
114
114
  - !ruby/object:Gem::Version
115
- version: 2.7.2
115
+ version: 2.7.3
116
116
  type: :runtime
117
117
  prerelease: false
118
118
  version_requirements: !ruby/object:Gem::Requirement
@@ -122,7 +122,7 @@ dependencies:
122
122
  version: '2.7'
123
123
  - - ">="
124
124
  - !ruby/object:Gem::Version
125
- version: 2.7.2
125
+ version: 2.7.3
126
126
  - !ruby/object:Gem::Dependency
127
127
  name: rqrcode
128
128
  requirement: !ruby/object:Gem::Requirement