trace_viz 1.0.0 → 1.0.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.
Files changed (74) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +63 -41
  3. data/lib/trace_viz/builders/base_builder.rb +11 -0
  4. data/lib/trace_viz/builders/diagram/base_builder.rb +10 -0
  5. data/lib/trace_viz/builders/diagram/message_builder.rb +96 -0
  6. data/lib/trace_viz/builders/diagram/sequence_builder.rb +50 -0
  7. data/lib/trace_viz/collectors/filters/base_class_filter.rb +3 -1
  8. data/lib/trace_viz/config/validator.rb +1 -1
  9. data/lib/trace_viz/defaults/config.rb +4 -2
  10. data/lib/trace_viz/exporters/base_exporter.rb +26 -5
  11. data/lib/trace_viz/exporters/mermaid_exporter.rb +17 -0
  12. data/lib/trace_viz/exporters/registry.rb +2 -0
  13. data/lib/trace_viz/exporters/text_exporter.rb +2 -24
  14. data/lib/trace_viz/extractors/base_extractor.rb +17 -0
  15. data/lib/trace_viz/extractors/diagram/base_extractor.rb +18 -0
  16. data/lib/trace_viz/extractors/diagram/box_extractor.rb +50 -0
  17. data/lib/trace_viz/extractors/diagram/message_extractor.rb +23 -0
  18. data/lib/trace_viz/extractors/diagram/participant_extractor.rb +37 -0
  19. data/lib/trace_viz/extractors/diagram/processors/message_processor.rb +93 -0
  20. data/lib/trace_viz/formatters/base_formatter.rb +1 -0
  21. data/lib/trace_viz/formatters/base_formatter_factory.rb +23 -0
  22. data/lib/trace_viz/formatters/diagram/sequence/base_formatter.rb +14 -0
  23. data/lib/trace_viz/formatters/diagram/sequence/message_formatter.rb +37 -0
  24. data/lib/trace_viz/formatters/diagram_formatter.rb +10 -0
  25. data/lib/trace_viz/formatters/export/formatter_factory.rb +8 -13
  26. data/lib/trace_viz/formatters/export/summary_group_formatter.rb +1 -1
  27. data/lib/trace_viz/formatters/helpers/digram/action_helper.rb +17 -0
  28. data/lib/trace_viz/formatters/helpers/digram/result_helper.rb +39 -0
  29. data/lib/trace_viz/formatters/helpers/log/params_helper.rb +8 -4
  30. data/lib/trace_viz/formatters/helpers/log/result_helper.rb +3 -3
  31. data/lib/trace_viz/formatters/helpers/log/summary/params_helper.rb +8 -4
  32. data/lib/trace_viz/formatters/helpers/params_helper.rb +8 -4
  33. data/lib/trace_viz/formatters/helpers/result_helper.rb +4 -3
  34. data/lib/trace_viz/formatters/helpers/source_helper.rb +4 -3
  35. data/lib/trace_viz/formatters/helpers/summary/params_helper.rb +7 -3
  36. data/lib/trace_viz/formatters/helpers/summary/source_helper.rb +3 -3
  37. data/lib/trace_viz/formatters/log/formatter_factory.rb +8 -13
  38. data/lib/trace_viz/formatters/log/summary_group_formatter.rb +1 -1
  39. data/lib/trace_viz/helpers/config_helper.rb +4 -0
  40. data/lib/trace_viz/loggers/post_collection_logger.rb +9 -4
  41. data/lib/trace_viz/loggers/trace_logger.rb +3 -6
  42. data/lib/trace_viz/managers/diagram/participant_manager.rb +23 -0
  43. data/lib/trace_viz/models/box.rb +19 -0
  44. data/lib/trace_viz/models/diagram.rb +27 -0
  45. data/lib/trace_viz/models/message.rb +16 -0
  46. data/lib/trace_viz/models/participant.rb +18 -0
  47. data/lib/trace_viz/models.rb +8 -0
  48. data/lib/trace_viz/renderers/base_renderer.rb +6 -3
  49. data/lib/trace_viz/renderers/diagram/sequence_renderer.rb +59 -0
  50. data/lib/trace_viz/renderers/render_context.rb +2 -3
  51. data/lib/trace_viz/renderers/renderer_builder.rb +20 -0
  52. data/lib/trace_viz/renderers/renderer_factory.rb +10 -22
  53. data/lib/trace_viz/renderers/summary_renderer.rb +18 -6
  54. data/lib/trace_viz/renderers/verbose_renderer.rb +6 -6
  55. data/lib/trace_viz/shared/renderer_helper.rb +4 -25
  56. data/lib/trace_viz/syntax/mermaid/sequence_syntax.rb +99 -0
  57. data/lib/trace_viz/trace_data/base.rb +7 -0
  58. data/lib/trace_viz/trace_data/node.rb +9 -3
  59. data/lib/trace_viz/trace_data/root_node.rb +4 -0
  60. data/lib/trace_viz/trace_data/summary_node.rb +5 -9
  61. data/lib/trace_viz/trace_data/trace_point/base.rb +4 -0
  62. data/lib/trace_viz/trace_data/trace_point/method_call.rb +4 -0
  63. data/lib/trace_viz/transformers/base_transformer.rb +29 -0
  64. data/lib/trace_viz/transformers/summary_transformer.rb +70 -0
  65. data/lib/trace_viz/utils/alias_generator.rb +58 -0
  66. data/lib/trace_viz/utils/format/key_value_formatter.rb +42 -0
  67. data/lib/trace_viz/utils/format/value_truncator.rb +123 -0
  68. data/lib/trace_viz/utils.rb +8 -0
  69. data/lib/trace_viz/version.rb +1 -1
  70. metadata +38 -11
  71. data/lib/trace_viz/renderers/summary/node_processor.rb +0 -82
  72. data/lib/trace_viz/utils/format_utils/key_value_formatter.rb +0 -37
  73. data/lib/trace_viz/utils/format_utils/value_truncator.rb +0 -74
  74. data/lib/trace_viz/utils/format_utils.rb +0 -24
@@ -0,0 +1,58 @@
1
+ # frozen_string_literal: true
2
+
3
+ module TraceViz
4
+ module Utils
5
+ class AliasGenerator
6
+ COMPONENT_DELIMITER = "::"
7
+ ALIAS_DELIMITER = "_"
8
+
9
+ class << self
10
+ #
11
+ # Generates a unique alias for a given name and ensures it doesn't conflict
12
+ # with existing aliases.
13
+ #
14
+ def generate(name:, assigned_aliases:)
15
+ raise ArgumentError, "name cannot be nil" if name.nil?
16
+
17
+ # Break the name into components and extract initials
18
+ alias_candidate = extract_initials(name.to_s)
19
+
20
+ # Ensure the alias is unique
21
+ unique_alias = ensure_unique_alias(
22
+ candidate: alias_candidate,
23
+ assigned_aliases: assigned_aliases,
24
+ original_name: name,
25
+ )
26
+
27
+ # Record the alias in the map
28
+ assigned_aliases[name] = unique_alias
29
+ unique_alias
30
+ end
31
+
32
+ private
33
+
34
+ #
35
+ # Extracts initials from a namespaced string
36
+ #
37
+ def extract_initials(full_name)
38
+ parts = full_name.split(COMPONENT_DELIMITER)
39
+ initials = parts.map { |part| part.scan(/[A-Z]/).join }
40
+ initials.join(ALIAS_DELIMITER)
41
+ end
42
+
43
+ #
44
+ # Ensures the alias is unique by appending a counter if necessary
45
+ #
46
+ def ensure_unique_alias(candidate:, assigned_aliases:, original_name:)
47
+ unique_alias = candidate
48
+ counter = 1
49
+ while assigned_aliases.value?(unique_alias)
50
+ unique_alias = "#{candidate}#{ALIAS_DELIMITER}#{counter}"
51
+ counter += 1
52
+ end
53
+ unique_alias
54
+ end
55
+ end
56
+ end
57
+ end
58
+ end
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+
3
+ module TraceViz
4
+ module Utils
5
+ module Format
6
+ module KeyValueFormatter
7
+ DEFAULT_MODE = :name_and_value
8
+ VALID_MODES = [:name_and_value, :name_only, :value_only].freeze
9
+
10
+ class << self
11
+ def format_pairs(data, mode: DEFAULT_MODE)
12
+ validate_input(data)
13
+ formatter = build_formatter(mode)
14
+ data.map { |key, value| formatter.call(key, value) }.join(", ")
15
+ end
16
+
17
+ private
18
+
19
+ def validate_input(data)
20
+ raise ArgumentError,
21
+ "Expected a Hash for data, but received #{data.class}. Please pass a valid Hash." unless data.is_a?(Hash)
22
+ end
23
+
24
+ def build_formatter(mode)
25
+ unless VALID_MODES.include?(mode)
26
+ raise ArgumentError, "Invalid mode: #{mode}. Valid modes are: #{VALID_MODES.join(", ")}."
27
+ end
28
+
29
+ case mode
30
+ when :name_and_value
31
+ ->(key, value) { "#{key}: #{value}" }
32
+ when :name_only
33
+ ->(key, _) { key.to_s }
34
+ when :value_only
35
+ ->(_, value) { value.to_s }
36
+ end
37
+ end
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,123 @@
1
+ # frozen_string_literal: true
2
+
3
+ module TraceViz
4
+ module Utils
5
+ module Format
6
+ module ValueTruncator
7
+ DEFAULT_LENGTH = -1
8
+ VALID_DIRECTIONS = [:start, :end].freeze
9
+
10
+ class << self
11
+ def truncate(value, length: DEFAULT_LENGTH, direction: :end, hash_length: DEFAULT_LENGTH)
12
+ validate_params(length, direction, hash_length)
13
+
14
+ # Skip truncation if length is not positive
15
+ return value unless length.positive?
16
+
17
+ opts = {
18
+ value: value,
19
+ length: length,
20
+ direction: direction,
21
+ hash_length: hash_length,
22
+ }
23
+
24
+ case value
25
+ when String then truncate_string(opts)
26
+ when Array then truncate_array(opts)
27
+ when Hash then truncate_hash(opts)
28
+ else truncate_object(opts)
29
+ end
30
+ end
31
+
32
+ private
33
+
34
+ def validate_params(length, direction, hash_length)
35
+ validate_length(length)
36
+ validate_length(hash_length)
37
+ validate_direction(direction)
38
+ end
39
+
40
+ def validate_length(val)
41
+ return if val.is_a?(Integer) && (val.positive? || val == DEFAULT_LENGTH)
42
+
43
+ raise ArgumentError, "Invalid length: #{val}. Must be a positive Integer or -1."
44
+ end
45
+
46
+ def validate_direction(direction)
47
+ return if VALID_DIRECTIONS.include?(direction)
48
+
49
+ raise ArgumentError, "Invalid direction: #{direction}. Valid options are :start or :end."
50
+ end
51
+
52
+ def truncate_string(opts)
53
+ string = opts[:value]
54
+ length = opts[:length]
55
+ direction = opts[:direction]
56
+
57
+ return string if string.length <= length
58
+
59
+ case direction
60
+ when :start then "...#{string[-length..]}"
61
+ when :end then "#{string[0, length]}..."
62
+ end
63
+ end
64
+
65
+ def truncate_array(opts)
66
+ array = opts[:value]
67
+ length = opts[:length]
68
+
69
+ return array if array.size <= length
70
+
71
+ truncated = array.take(length)
72
+ truncated << "..." if array.size > length
73
+ truncated
74
+ end
75
+
76
+ def truncate_hash(opts)
77
+ hash = opts[:value]
78
+ length = opts[:length]
79
+ direction = opts[:direction]
80
+ hash_length = opts[:hash_length]
81
+
82
+ truncated_keys = hash.keys.take(length)
83
+
84
+ truncated_parts = truncated_keys.map do |key|
85
+ "#{key}: #{truncate(hash[key], **opts.except(:value))}"
86
+ end
87
+
88
+ truncated_parts << "..." if hash.size > length
89
+ format_hash(
90
+ content: truncated_parts.join(", "),
91
+ direction: direction,
92
+ hash_length: hash_length,
93
+ )
94
+ end
95
+
96
+ def format_hash(content:, direction:, hash_length:)
97
+ # Only truncate the final string if hash_length is positive
98
+ return "{#{content}}" unless hash_length.positive?
99
+
100
+ case direction
101
+ when :start then "{...#{content[-hash_length..]}}"
102
+ when :end then "{#{content[0, hash_length]}...}"
103
+ end
104
+ end
105
+
106
+ def truncate_object(opts)
107
+ object = opts[:value]
108
+ length = opts[:length]
109
+ direction = opts[:direction]
110
+
111
+ object_str = object.inspect
112
+ return object_str if object_str.length <= length
113
+
114
+ case direction
115
+ when :start then "#{object.class}(...#{object_str[-length..]})"
116
+ when :end then "#{object.class}(#{object_str[0, length]}...)"
117
+ end
118
+ end
119
+ end
120
+ end
121
+ end
122
+ end
123
+ end
@@ -0,0 +1,8 @@
1
+ # frozen_string_literal: true
2
+
3
+ Dir[File.join(__dir__, "utils/**/*.rb")].each { |file| require_relative file }
4
+
5
+ module TraceViz
6
+ module Utils
7
+ end
8
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module TraceViz
4
- VERSION = "1.0.0"
4
+ VERSION = "1.0.1"
5
5
  end
metadata CHANGED
@@ -1,18 +1,17 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: trace_viz
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.0
4
+ version: 1.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Huy Nguyen
8
- autorequire:
8
+ autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2025-01-04 00:00:00.000000000 Z
11
+ date: 2025-03-04 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: "TraceViz is a Ruby library designed to trace and visualize events executed
14
- \nin a block of code. Useful for debugging and logging. \nDiagram generation is
15
- currently under development.\n"
14
+ \nin a block of code. Useful for debugging and logging.\n"
16
15
  email:
17
16
  - patrick204nqh@gmail.com
18
17
  executables: []
@@ -36,6 +35,10 @@ files:
36
35
  - lib/trace_viz.rb
37
36
  - lib/trace_viz/adapters/base_adapter.rb
38
37
  - lib/trace_viz/adapters/trace_point_adapter.rb
38
+ - lib/trace_viz/builders/base_builder.rb
39
+ - lib/trace_viz/builders/diagram/base_builder.rb
40
+ - lib/trace_viz/builders/diagram/message_builder.rb
41
+ - lib/trace_viz/builders/diagram/sequence_builder.rb
39
42
  - lib/trace_viz/collectors/base_collector.rb
40
43
  - lib/trace_viz/collectors/filters/base_class_filter.rb
41
44
  - lib/trace_viz/collectors/filters/base_exclude_filter.rb
@@ -87,9 +90,20 @@ files:
87
90
  - lib/trace_viz/errors.rb
88
91
  - lib/trace_viz/exporters/base_exporter.rb
89
92
  - lib/trace_viz/exporters/export_manager.rb
93
+ - lib/trace_viz/exporters/mermaid_exporter.rb
90
94
  - lib/trace_viz/exporters/registry.rb
91
95
  - lib/trace_viz/exporters/text_exporter.rb
96
+ - lib/trace_viz/extractors/base_extractor.rb
97
+ - lib/trace_viz/extractors/diagram/base_extractor.rb
98
+ - lib/trace_viz/extractors/diagram/box_extractor.rb
99
+ - lib/trace_viz/extractors/diagram/message_extractor.rb
100
+ - lib/trace_viz/extractors/diagram/participant_extractor.rb
101
+ - lib/trace_viz/extractors/diagram/processors/message_processor.rb
92
102
  - lib/trace_viz/formatters/base_formatter.rb
103
+ - lib/trace_viz/formatters/base_formatter_factory.rb
104
+ - lib/trace_viz/formatters/diagram/sequence/base_formatter.rb
105
+ - lib/trace_viz/formatters/diagram/sequence/message_formatter.rb
106
+ - lib/trace_viz/formatters/diagram_formatter.rb
93
107
  - lib/trace_viz/formatters/export/base_formatter.rb
94
108
  - lib/trace_viz/formatters/export/formatter_factory.rb
95
109
  - lib/trace_viz/formatters/export/method_call_formatter.rb
@@ -97,6 +111,8 @@ files:
97
111
  - lib/trace_viz/formatters/export/summary_group_formatter.rb
98
112
  - lib/trace_viz/formatters/helpers.rb
99
113
  - lib/trace_viz/formatters/helpers/depth_helper.rb
114
+ - lib/trace_viz/formatters/helpers/digram/action_helper.rb
115
+ - lib/trace_viz/formatters/helpers/digram/result_helper.rb
100
116
  - lib/trace_viz/formatters/helpers/indent_helper.rb
101
117
  - lib/trace_viz/formatters/helpers/log/color_helper.rb
102
118
  - lib/trace_viz/formatters/helpers/log/depth_helper.rb
@@ -129,14 +145,22 @@ files:
129
145
  - lib/trace_viz/loggers/post_collection_logger.rb
130
146
  - lib/trace_viz/loggers/trace_logger.rb
131
147
  - lib/trace_viz/loggers/trace_stats_logger.rb
148
+ - lib/trace_viz/managers/diagram/participant_manager.rb
149
+ - lib/trace_viz/models.rb
150
+ - lib/trace_viz/models/box.rb
151
+ - lib/trace_viz/models/diagram.rb
152
+ - lib/trace_viz/models/message.rb
153
+ - lib/trace_viz/models/participant.rb
132
154
  - lib/trace_viz/renderers/base_renderer.rb
155
+ - lib/trace_viz/renderers/diagram/sequence_renderer.rb
133
156
  - lib/trace_viz/renderers/render_context.rb
157
+ - lib/trace_viz/renderers/renderer_builder.rb
134
158
  - lib/trace_viz/renderers/renderer_factory.rb
135
- - lib/trace_viz/renderers/summary/node_processor.rb
136
159
  - lib/trace_viz/renderers/summary_renderer.rb
137
160
  - lib/trace_viz/renderers/verbose_renderer.rb
138
161
  - lib/trace_viz/shared.rb
139
162
  - lib/trace_viz/shared/renderer_helper.rb
163
+ - lib/trace_viz/syntax/mermaid/sequence_syntax.rb
140
164
  - lib/trace_viz/trace_data/base.rb
141
165
  - lib/trace_viz/trace_data/node.rb
142
166
  - lib/trace_viz/trace_data/root_node.rb
@@ -149,10 +173,13 @@ files:
149
173
  - lib/trace_viz/traits/depth_trackable.rb
150
174
  - lib/trace_viz/traits/identifiable.rb
151
175
  - lib/trace_viz/traits/time_trackable.rb
176
+ - lib/trace_viz/transformers/base_transformer.rb
177
+ - lib/trace_viz/transformers/summary_transformer.rb
178
+ - lib/trace_viz/utils.rb
179
+ - lib/trace_viz/utils/alias_generator.rb
152
180
  - lib/trace_viz/utils/colorize.rb
153
- - lib/trace_viz/utils/format_utils.rb
154
- - lib/trace_viz/utils/format_utils/key_value_formatter.rb
155
- - lib/trace_viz/utils/format_utils/value_truncator.rb
181
+ - lib/trace_viz/utils/format/key_value_formatter.rb
182
+ - lib/trace_viz/utils/format/value_truncator.rb
156
183
  - lib/trace_viz/utils/id_generator.rb
157
184
  - lib/trace_viz/version.rb
158
185
  - sig/adapters/base_adapter.rbs
@@ -185,7 +212,7 @@ metadata:
185
212
  homepage_uri: https://github.com/patrick204nqh/trace_viz
186
213
  source_code_uri: https://github.com/patrick204nqh/trace_viz
187
214
  changelog_uri: https://github.com/patrick204nqh/trace_viz/blob/main/CHANGELOG.md
188
- post_install_message:
215
+ post_install_message:
189
216
  rdoc_options: []
190
217
  require_paths:
191
218
  - lib
@@ -201,7 +228,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
201
228
  version: '0'
202
229
  requirements: []
203
230
  rubygems_version: 3.5.3
204
- signing_key:
231
+ signing_key:
205
232
  specification_version: 4
206
233
  summary: Trace method and attribute usage in Ruby classes and generate diagrams.
207
234
  test_files: []
@@ -1,82 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require "trace_viz/trace_data/summary_node"
4
-
5
- module TraceViz
6
- module Renderers
7
- class NodeProcessor
8
- def initialize(nodes, context)
9
- @nodes = nodes
10
- @context = context
11
- end
12
-
13
- def process
14
- grouped_nodes.flat_map { |key, group| render_node_or_group(key, group) }
15
- end
16
-
17
- private
18
-
19
- attr_reader :nodes, :context
20
-
21
- def grouped_nodes
22
- nodes.group_by { |node| node_key(node) }
23
- end
24
-
25
- def group_keys
26
- context.group_keys
27
- end
28
-
29
- def node_key(node)
30
- group_keys.map { |key| fetch_node_attribute(node, key) }
31
- end
32
-
33
- def fetch_node_attribute(node, key)
34
- node.respond_to?(key) ? node.public_send(key) : nil
35
- end
36
-
37
- def render_node_or_group(key, group)
38
- if group.size > 1
39
- render_group(key, group)
40
- else
41
- render_single_node(group.first)
42
- end
43
- end
44
-
45
- def render_group(key, group)
46
- representative_node = group.first
47
- nested_lines = process_nested_nodes(representative_node)
48
-
49
- [{
50
- line: format_group_line(group),
51
- trace_data: representative_node,
52
- nested_lines: nested_lines,
53
- }]
54
- end
55
-
56
- def render_single_node(node)
57
- current_line = {
58
- line: format_node(node),
59
- trace_data: node,
60
- nested_lines: process_nested_nodes(node),
61
- }
62
-
63
- [current_line]
64
- end
65
-
66
- def process_nested_nodes(node)
67
- return [] unless node.respond_to?(:children) && node.children.any?
68
-
69
- NodeProcessor.new(node.children, context).process
70
- end
71
-
72
- def format_node(node)
73
- context.fetch_formatter(node.event).call(node)
74
- end
75
-
76
- def format_group_line(group)
77
- node = TraceData::SummaryNode.new(group: group)
78
- context.fetch_formatter(:summary_group).call(node)
79
- end
80
- end
81
- end
82
- end
@@ -1,37 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module TraceViz
4
- module Utils
5
- module FormatUtils
6
- class KeyValueFormatter
7
- DEFAULT_MODE = :name_and_value
8
-
9
- def initialize(mode: DEFAULT_MODE)
10
- @mode = mode
11
- @formatter = build_formatter
12
- end
13
-
14
- def call(data)
15
- validate_input(data)
16
- data.map { |key, value| @formatter.call(key, value) }.join(", ")
17
- end
18
-
19
- private
20
-
21
- def validate_input(data)
22
- unless data.is_a?(Hash)
23
- raise ArgumentError, "Expected a Hash for key-value formatting, got #{data.class}"
24
- end
25
- end
26
-
27
- def build_formatter
28
- {
29
- name_and_value: ->(key, value) { "#{key}: #{value}" },
30
- name_only: ->(key, _) { key.to_s },
31
- value_only: ->(_, value) { value.to_s },
32
- }.fetch(@mode) { raise ArgumentError, "Invalid mode: #{@mode}" }
33
- end
34
- end
35
- end
36
- end
37
- end
@@ -1,74 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module TraceViz
4
- module Utils
5
- module FormatUtils
6
- class ValueTruncator
7
- DEFAULT_LENGTH = -1
8
- VALID_DIRECTIONS = [:start, :end].freeze
9
-
10
- def initialize(length: DEFAULT_LENGTH, direction: :end)
11
- @length = length
12
- @direction = validate_direction(direction)
13
- end
14
-
15
- def truncate(value)
16
- return value unless valid_length?
17
-
18
- case value
19
- when String then truncate_string(value)
20
- when Array then truncate_array(value)
21
- when Hash then truncate_hash(value)
22
- else truncate_generic(value)
23
- end
24
- end
25
-
26
- private
27
-
28
- attr_reader :length, :direction
29
-
30
- def validate_direction(direction)
31
- return direction if VALID_DIRECTIONS.include?(direction)
32
-
33
- raise ArgumentError, "Invalid direction: #{direction}. Valid options are :start or :end."
34
- end
35
-
36
- def valid_length?
37
- length.is_a?(Integer) && length.positive?
38
- end
39
-
40
- def truncate_string(string)
41
- return string if string.length <= length
42
-
43
- case direction
44
- when :start then "...#{string[-length..]}"
45
- when :end then "#{string[0, length]}..."
46
- end
47
- end
48
-
49
- def truncate_array(array)
50
- truncated = array.take(length)
51
- truncated << "..." if array.size > length
52
- truncated
53
- end
54
-
55
- def truncate_hash(hash)
56
- keys = hash.keys.take(length)
57
- truncated_pairs = keys.map { |key| "#{key}: #{truncate(hash[key])}" }
58
- truncated_pairs << "..." if hash.size > length
59
- "{#{truncated_pairs.join(", ")}}"
60
- end
61
-
62
- def truncate_generic(object)
63
- object_str = object.inspect
64
- return object_str if object_str.length <= length
65
-
66
- case direction
67
- when :start then "#{object.class}(...#{object_str[-length..]})"
68
- when :end then "#{object.class}(#{object_str[0, length]}...)"
69
- end
70
- end
71
- end
72
- end
73
- end
74
- end
@@ -1,24 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require_relative "format_utils/key_value_formatter"
4
- require_relative "format_utils/value_truncator"
5
-
6
- module TraceViz
7
- module Utils
8
- module FormatUtils
9
- class << self
10
- # Formats key-value pairs based on the provided mode
11
- def format_key_value_pairs(data, mode)
12
- formatter = KeyValueFormatter.new(mode: mode)
13
- formatter.call(data)
14
- end
15
-
16
- # Truncates a value to the specified length
17
- def truncate_value(value, length, direction: :end)
18
- truncator = ValueTruncator.new(length: length, direction: direction)
19
- truncator.truncate(value)
20
- end
21
- end
22
- end
23
- end
24
- end