ace-bundle 0.40.0 → 0.40.1

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: 224cd0cec9e0e96eb99b0fa393dfbeeb9807012a5499538c5a55fb5e23e5d714
4
- data.tar.gz: 95c22bd2455c263af3be4240a9e918379215f99b17689b44ff1e6acdfe496445
3
+ metadata.gz: b3398d18b96bc1a9cb8763ed6c739dee4cc2c43a96645bab10fc6852c9c76110
4
+ data.tar.gz: d17a1fc03f51619399f4102bb7f308ca93c0751394e6c43901632ec057293229
5
5
  SHA512:
6
- metadata.gz: 65c7f0e6416fa29a473dc9aab623bfa2f79348ea4e4797a5519529a6677061f973368afcdb98ba292cb1007502e514427d5bb9002dc97d27fd48082aa080f4df
7
- data.tar.gz: 92e6630b7917e3ba60dd69abef6e01fe4091c2228d93b7603ada68f1cc5920cf6adca53acc7c5690d4428171f7ece6f8533b23847c6afeaf739f3837bdaed803
6
+ metadata.gz: 29445cdb859605821f2a81a6f59b2eb255a0154d85e6871171d4fb82fca38574b3fec150df75a68c3a4e2acf14a6b76a72301792945680c35f952d4a7352cea5
7
+ data.tar.gz: a7539e8729b4263d227b42f1b593d8d0bc180a7c52b5df6f53bd38352ef351c240e67969d89a4efc9b0177f1a88937a841d75a270eb0fea69d23f8b78a0de258
data/CHANGELOG.md CHANGED
@@ -6,6 +6,11 @@ The format is based on [Keep a Changelog][1], and this project adheres to [Seman
6
6
 
7
7
  ## [Unreleased]
8
8
 
9
+ ## [0.40.1] - 2026-03-23
10
+
11
+ ### Added
12
+ - Display compression statistics line above "Bundle saved" output when compression is active, showing original vs compressed size and line count with percentage reduction.
13
+
9
14
  ## [0.40.0] - 2026-03-23
10
15
 
11
16
  ### Changed
@@ -266,6 +266,7 @@ module Ace
266
266
  result = Ace::Bundle.write_output(context, cache_file, options)
267
267
 
268
268
  if result[:success]
269
+ display_compression_stats(context, result)
269
270
  if result[:chunked]
270
271
  chunks = result[:results].select { |r| r[:file_type] == "chunk" }
271
272
  total_lines = chunks.sum { |r| r[:lines] || 0 }
@@ -288,6 +289,7 @@ module Ace
288
289
  result = Ace::Bundle.write_output(context, file_path, options)
289
290
 
290
291
  if result[:success]
292
+ display_compression_stats(context, result)
291
293
  if result[:chunked]
292
294
  chunks = result[:results].select { |r| r[:file_type] == "chunk" }
293
295
  total_lines = chunks.sum { |r| r[:lines] || 0 }
@@ -303,6 +305,29 @@ module Ace
303
305
  end
304
306
  end
305
307
 
308
+ def display_compression_stats(context, result)
309
+ stats = context&.metadata&.dig(:compression_stats)
310
+ return unless stats
311
+
312
+ orig_b = stats[:original_bytes]
313
+ comp_b = stats[:compressed_bytes]
314
+ return if orig_b.zero? || orig_b == comp_b
315
+
316
+ # Use actual bundle size and compute what uncompressed bundle would have been
317
+ bundle_bytes = context.content.to_s.bytesize
318
+ bundle_lines = result[:lines] || context.content.to_s.lines.count
319
+ overhead_bytes = bundle_bytes - comp_b
320
+ overhead_lines = bundle_lines - stats[:compressed_lines]
321
+ total_orig_bytes = orig_b + overhead_bytes
322
+ total_orig_lines = stats[:original_lines] + overhead_lines
323
+
324
+ byte_pct = ((bundle_bytes - total_orig_bytes) * 100.0 / total_orig_bytes).round(1)
325
+ line_pct = ((bundle_lines - total_orig_lines) * 100.0 / total_orig_lines).round(1)
326
+
327
+ puts "Compressed: #{format_size(total_orig_bytes)} → #{format_size(bundle_bytes)} (#{byte_pct}%), " \
328
+ "#{total_orig_lines} → #{bundle_lines} lines (#{line_pct}%)"
329
+ end
330
+
306
331
  def format_size(bytes)
307
332
  units = ["B", "KB", "MB", "GB"]
308
333
  size = bytes.to_f
@@ -30,8 +30,11 @@ module Ace
30
30
  # @param bundle_data [Models::BundleData] bundle with sections
31
31
  # @return [Models::BundleData] same bundle with compressed file content
32
32
  def call(bundle_data)
33
+ original_bytes, original_lines = measure_compressible_content(bundle_data)
34
+
33
35
  unless bundle_data.has_sections?
34
36
  compress_content(bundle_data) if @default_mode != "off"
37
+ store_compression_stats(bundle_data, original_bytes, original_lines)
35
38
  return bundle_data
36
39
  end
37
40
 
@@ -42,6 +45,7 @@ module Ace
42
45
  compress_section_files(section_data, section_mode)
43
46
  end
44
47
 
48
+ store_compression_stats(bundle_data, original_bytes, original_lines)
45
49
  bundle_data
46
50
  end
47
51
 
@@ -243,6 +247,39 @@ module Ace
243
247
  source_kind: source_kind
244
248
  }
245
249
  end
250
+
251
+ def measure_compressible_content(bundle_data)
252
+ if bundle_data.has_sections?
253
+ bytes = 0
254
+ lines = 0
255
+ bundle_data.sections.each do |_, section_data|
256
+ (section_data[:_processed_files] || []).each do |f|
257
+ next unless compressible?(f[:path])
258
+
259
+ content = f[:content].to_s
260
+ bytes += content.bytesize
261
+ lines += content.lines.count
262
+ end
263
+ end
264
+ [bytes, lines]
265
+ else
266
+ content = bundle_data.content.to_s
267
+ [content.bytesize, content.lines.count]
268
+ end
269
+ end
270
+
271
+ def store_compression_stats(bundle_data, original_bytes, original_lines)
272
+ compressed_bytes, compressed_lines = measure_compressible_content(bundle_data)
273
+ return if original_bytes.zero?
274
+ return if original_bytes == compressed_bytes && original_lines == compressed_lines
275
+
276
+ bundle_data.metadata[:compression_stats] = {
277
+ original_bytes: original_bytes,
278
+ compressed_bytes: compressed_bytes,
279
+ original_lines: original_lines,
280
+ compressed_lines: compressed_lines
281
+ }
282
+ end
246
283
  end
247
284
  end
248
285
  end
@@ -1087,11 +1087,23 @@ module Ace
1087
1087
  content = bundle.content.to_s
1088
1088
  return if content.strip.empty?
1089
1089
 
1090
+ original_bytes = content.bytesize
1091
+ original_lines = content.lines.count
1092
+
1090
1093
  require "ace/compressor"
1091
1094
  label = bundle.metadata[:source]&.to_s || "bundle.md"
1092
1095
  compressed = Ace::Compressor.compress_text(content, label: label, mode: compressor_mode)
1093
1096
  bundle.content = compressed
1094
1097
  bundle.metadata[:compressed] = true
1098
+
1099
+ if original_bytes > 0 && compressed.bytesize != original_bytes
1100
+ bundle.metadata[:compression_stats] = {
1101
+ original_bytes: original_bytes,
1102
+ compressed_bytes: compressed.bytesize,
1103
+ original_lines: original_lines,
1104
+ compressed_lines: compressed.lines.count
1105
+ }
1106
+ end
1095
1107
  end
1096
1108
 
1097
1109
  def sections_have_processed_files?(bundle)
@@ -2,6 +2,6 @@
2
2
 
3
3
  module Ace
4
4
  module Bundle
5
- VERSION = "0.40.0"
5
+ VERSION = "0.40.1"
6
6
  end
7
7
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ace-bundle
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.40.0
4
+ version: 0.40.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Michal Czyz