trace_viz 0.0.1 → 0.0.2

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 (77) hide show
  1. checksums.yaml +4 -4
  2. data/CONTRIBUTING.md +34 -0
  3. data/README.md +130 -38
  4. data/examples/example.cast +285 -0
  5. data/examples/example.rb +94 -23
  6. data/lib/trace_viz/adapters/base_adapter.rb +0 -2
  7. data/lib/trace_viz/adapters/trace_point_adapter.rb +17 -11
  8. data/lib/trace_viz/collectors/base_collector.rb +83 -0
  9. data/lib/trace_viz/collectors/depth_manager.rb +37 -0
  10. data/lib/trace_viz/collectors/evaluators/base_evaluator.rb +23 -0
  11. data/lib/trace_viz/collectors/evaluators/filter_evaluator.rb +30 -0
  12. data/lib/trace_viz/collectors/evaluators/hidden_evaluator.rb +21 -0
  13. data/lib/trace_viz/collectors/filters/base_filter.rb +23 -0
  14. data/lib/trace_viz/collectors/filters/exclude_classes_filter.rb +28 -0
  15. data/lib/trace_viz/collectors/filters/exclude_default_classes_filter.rb +38 -0
  16. data/lib/trace_viz/collectors/filters/exclude_gems_filter.rb +30 -0
  17. data/lib/trace_viz/collectors/filters/exclude_internal_call_filter.rb +31 -0
  18. data/lib/trace_viz/collectors/filters/exclude_rails_framework_filter.rb +38 -0
  19. data/lib/trace_viz/collectors/filters/include_classes_filter.rb +28 -0
  20. data/lib/trace_viz/collectors/filters/include_gems_filter.rb +54 -0
  21. data/lib/trace_viz/collectors/filters/registry.rb +59 -0
  22. data/lib/trace_viz/collectors/matchers/trace_point_action_matcher.rb +36 -0
  23. data/lib/trace_viz/collectors/matchers/within_depth_matcher.rb +25 -0
  24. data/lib/trace_viz/collectors/trace_point_collector.rb +51 -0
  25. data/lib/trace_viz/collectors/trace_stats.rb +21 -0
  26. data/lib/trace_viz/config/copier.rb +38 -0
  27. data/lib/trace_viz/config/validator.rb +74 -0
  28. data/lib/trace_viz/configuration.rb +36 -30
  29. data/lib/trace_viz/context/config_context.rb +1 -1
  30. data/lib/trace_viz/context/manager.rb +17 -21
  31. data/lib/trace_viz/context/map.rb +29 -0
  32. data/lib/trace_viz/context/registry.rb +37 -0
  33. data/lib/trace_viz/context/tracking/active_calls.rb +37 -0
  34. data/lib/trace_viz/context/tracking_context.rb +7 -2
  35. data/lib/trace_viz/context.rb +2 -2
  36. data/lib/trace_viz/core/tracer.rb +1 -0
  37. data/lib/trace_viz/defaults.rb +139 -0
  38. data/lib/trace_viz/exporters/base_exporter.rb +84 -0
  39. data/lib/trace_viz/exporters/formatters/base_formatter.rb +12 -0
  40. data/lib/trace_viz/exporters/formatters/method_call_formatter.rb +21 -0
  41. data/lib/trace_viz/exporters/formatters/method_return_formatter.rb +22 -0
  42. data/lib/trace_viz/exporters/text_exporter.rb +15 -0
  43. data/lib/trace_viz/exporters/transformers/base_transformer.rb +25 -0
  44. data/lib/trace_viz/exporters/transformers/text_transformer.rb +28 -0
  45. data/lib/trace_viz/formatters/base_formatter.rb +42 -0
  46. data/lib/trace_viz/formatters/helpers/depth_helper.rb +21 -0
  47. data/lib/trace_viz/formatters/helpers/indent_helper.rb +15 -0
  48. data/lib/trace_viz/formatters/helpers/method_details_helper.rb +15 -0
  49. data/lib/trace_viz/formatters/helpers/params_helper.rb +26 -0
  50. data/lib/trace_viz/formatters/helpers/result_helper.rb +21 -0
  51. data/lib/trace_viz/formatters/helpers/source_helper.rb +21 -0
  52. data/lib/trace_viz/formatters/helpers/time_helper.rb +15 -0
  53. data/lib/trace_viz/logger.rb +37 -47
  54. data/lib/trace_viz/loggers/trace_builder.rb +30 -0
  55. data/lib/trace_viz/loggers/trace_formatters/base_formatter.rb +32 -0
  56. data/lib/trace_viz/loggers/trace_formatters/method_call_formatter.rb +21 -0
  57. data/lib/trace_viz/loggers/trace_formatters/method_return_formatter.rb +22 -0
  58. data/lib/trace_viz/loggers/trace_logger.rb +38 -0
  59. data/lib/trace_viz/loggers/trace_stats_logger.rb +33 -0
  60. data/lib/trace_viz/trace_data/base.rb +56 -0
  61. data/lib/trace_viz/trace_data/trace_point/base.rb +68 -0
  62. data/lib/trace_viz/trace_data/trace_point/method_call.rb +42 -0
  63. data/lib/trace_viz/trace_data/trace_point/method_return.rb +25 -0
  64. data/lib/trace_viz/trace_data/trace_point_builder.rb +23 -0
  65. data/lib/trace_viz/utils/colorize.rb +12 -23
  66. data/lib/trace_viz/utils/format_utils.rb +67 -0
  67. data/lib/trace_viz/version.rb +1 -1
  68. metadata +58 -13
  69. data/lib/trace_viz/adapters/trace_point/depth_manager.rb +0 -34
  70. data/lib/trace_viz/adapters/trace_point/event_handler.rb +0 -36
  71. data/lib/trace_viz/adapters/trace_point/trace_data.rb +0 -89
  72. data/lib/trace_viz/adapters/trace_point/trace_formatter.rb +0 -95
  73. data/lib/trace_viz/adapters/trace_point/trace_logger.rb +0 -44
  74. data/lib/trace_viz/context/manager/context_map.rb +0 -31
  75. data/lib/trace_viz/context/manager/context_operations.rb +0 -60
  76. data/lib/trace_viz/context/manager/context_registry.rb +0 -20
  77. data/lib/trace_viz/context/manager/context_validation.rb +0 -34
@@ -0,0 +1,38 @@
1
+ # frozen_string_literal: true
2
+
3
+ module TraceViz
4
+ module Config
5
+ class Copier
6
+ def initialize(configuration)
7
+ @origin_configuration = configuration
8
+ @settings = origin_configuration.settings
9
+ end
10
+
11
+ def copy
12
+ copied_settings = deep_copy(settings)
13
+ copy = origin_configuration.class.new
14
+ copied_settings.each { |key, value| copy.update(key, value) }
15
+ copy
16
+ end
17
+
18
+ private
19
+
20
+ attr_reader :origin_configuration, :settings
21
+
22
+ def deep_copy(value)
23
+ case value
24
+ when Hash
25
+ value.transform_values { |v| deep_copy(v) }
26
+ when Array
27
+ value.map { |v| deep_copy(v) }
28
+ else
29
+ begin
30
+ value.dup
31
+ rescue TypeError
32
+ value # Return immutable objects as-is
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,74 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "trace_viz/collectors/filters/registry"
4
+
5
+ module TraceViz
6
+ module Config
7
+ class Validator
8
+ FILTER_KEYS = Collectors::Filters::Registry::FILTERS.keys.freeze
9
+
10
+ def initialize
11
+ @validations = {
12
+ params: ->(value) { validate_params(value) },
13
+ result: ->(value) { validate_result(value) },
14
+ source_location: ->(value) { validate_source_location(value) },
15
+ filters: ->(value) { validate_filters(value) },
16
+ export: ->(value) { validate_export(value) },
17
+ }
18
+ end
19
+
20
+ def validate(group, value)
21
+ return unless @validations.key?(group)
22
+
23
+ @validations[group].call(value)
24
+ end
25
+
26
+ private
27
+
28
+ def validate_params(value)
29
+ mode = value[:mode]
30
+ unless Defaults.valid_param_modes.include?(mode)
31
+ raise ArgumentError, "Invalid param mode: #{mode}. Valid modes are #{Defaults.valid_param_modes.join(", ")}."
32
+ end
33
+
34
+ if value[:truncate_values] && (!value[:truncate_values].is_a?(Integer) || value[:truncate_values] <= 0)
35
+ raise ArgumentError, "Truncate values must be a positive integer."
36
+ end
37
+ end
38
+
39
+ def validate_result(value)
40
+ if value[:truncate_length] && (!value[:truncate_length].is_a?(Integer) || value[:truncate_length] <= 0)
41
+ raise ArgumentError, "Truncate values must be a positive integer."
42
+ end
43
+ end
44
+
45
+ def validate_source_location(value)
46
+ if value[:truncate_length] && (!value[:truncate_length].is_a?(Integer) || value[:truncate_length] <= 0)
47
+ raise ArgumentError, "Truncate length for source_location must be a positive integer."
48
+ end
49
+
50
+ if value[:filter_paths] && !value[:filter_paths].all? { |path| path.is_a?(Regexp) }
51
+ raise ArgumentError, "All filter paths must be regular expressions."
52
+ end
53
+ end
54
+
55
+ def validate_filters(filters)
56
+ unless filters.is_a?(Array)
57
+ raise ArgumentError, "Filters must be an array. Received: #{filters.class.name}"
58
+ end
59
+ end
60
+
61
+ def validate_export(value)
62
+ unless value.is_a?(Hash)
63
+ raise ArgumentError, "Export configuration must be a hash."
64
+ end
65
+
66
+ format = value[:format]
67
+ unless Defaults.valid_export_formats.include?(format)
68
+ raise ArgumentError,
69
+ "Invalid export format: #{format}. Valid formats are #{Defaults.valid_export_formats.join(", ")}."
70
+ end
71
+ end
72
+ end
73
+ end
74
+ end
@@ -1,47 +1,53 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require "trace_viz/logger"
4
+ require "trace_viz/config/validator"
5
+ require "trace_viz/config/copier"
4
6
 
5
7
  module TraceViz
6
8
  class Configuration
7
- attr_accessor :logger,
8
- :tab_size,
9
- :show_indent,
10
- :show_depth,
11
- :max_display_depth,
12
- :show_method_name,
13
- :show_source_location,
14
- :show_params,
15
- :show_return_value,
16
- :show_execution_time,
17
- :show_trace_events
9
+ attr_reader :logger, :settings
10
+ attr_reader(*Defaults.fetch_defaults.keys)
18
11
 
19
12
  def initialize
20
13
  @logger = Logger.new
21
- @tab_size = 2
22
- @show_indent = true
23
- @show_depth = true
24
- @max_display_depth = 3 # Recommended to keep this value between 3 and 5
25
- @show_method_name = true
26
- @show_source_location = false
27
- @show_params = true
28
- @show_return_value = true
29
- @show_execution_time = true
30
- @show_trace_events = [:call, :return]
14
+ @validator = Config::Validator.new
15
+ @settings = Defaults.fetch_defaults
16
+ define_dynamic_accessors
17
+ end
18
+
19
+ def [](key)
20
+ settings[key]
21
+ end
22
+
23
+ def update(group, values)
24
+ raise ArgumentError, "Invalid configuration group: #{group}" unless settings.key?(group)
25
+
26
+ @validator.validate(group, values)
27
+ if settings[group].is_a?(Hash)
28
+ settings[group].merge!(values)
29
+ else
30
+ settings[group] = values
31
+ end
32
+ end
33
+
34
+ def reset_defaults
35
+ @settings = Defaults.fetch_defaults
31
36
  end
32
37
 
33
38
  def dup
34
- copy = self.class.new
35
- instance_variables.each do |var|
36
- value = instance_variable_get(var)
37
- copy_value = begin
38
- value.dup
39
- rescue TypeError
40
- value
39
+ Config::Copier.new(self).copy
40
+ end
41
+
42
+ private
43
+
44
+ def define_dynamic_accessors
45
+ settings.each_key do |attr|
46
+ define_singleton_method(attr) { settings[attr] }
47
+ define_singleton_method("#{attr}=") do |value|
48
+ update(attr, value)
41
49
  end
42
- copy.instance_variable_set(var, copy_value)
43
50
  end
44
- copy
45
51
  end
46
52
  end
47
53
 
@@ -23,7 +23,7 @@ module TraceViz
23
23
  if temp_configuration.respond_to?("#{key}=")
24
24
  temp_configuration.send("#{key}=", value)
25
25
  else
26
- warn("TraceViz: Unknown configuration option '#{key}'")
26
+ TraceViz.logger.warn("Unknown configuration option '#{key}'")
27
27
  end
28
28
  end
29
29
 
@@ -1,37 +1,33 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require "trace_viz/context/manager/context_map"
4
- require "trace_viz/context/manager/context_validation"
5
- require "trace_viz/context/manager/context_registry"
6
- require "trace_viz/context/manager/context_operations"
7
- require "trace_viz/context/config_context"
8
- require "trace_viz/context/tracking_context"
3
+ require "trace_viz/context/map"
4
+ require "trace_viz/context/registry"
9
5
 
10
6
  module TraceViz
11
7
  module Context
12
8
  class Manager
9
+ @map = Map.new
10
+
13
11
  class << self
14
- include ContextMap
15
- include ContextValidation
16
- include ContextRegistry
17
- include ContextOperations
12
+ def enter_contexts(contexts)
13
+ @map.replace(Registry.build(contexts))
14
+ end
18
15
 
19
- # Initialize class instance variables
20
- def initialize_manager
21
- @context_map = {}
22
- @registered_contexts = {}
16
+ def exit_contexts(*keys)
17
+ @map.remove(*keys)
18
+ end
23
19
 
24
- register_default_contexts
20
+ def with_contexts(contexts = {})
21
+ enter_contexts(contexts)
22
+ yield
23
+ ensure
24
+ exit_contexts(*contexts.keys)
25
25
  end
26
26
 
27
- def register_default_contexts
28
- Manager.register_context_type(:config, ConfigContext)
29
- Manager.register_context_type(:tracking, TrackingContext)
27
+ def fetch_context(key)
28
+ @map.fetch(key)
30
29
  end
31
30
  end
32
-
33
- # Ensure initialization upon loading
34
- initialize_manager
35
31
  end
36
32
  end
37
33
  end
@@ -0,0 +1,29 @@
1
+ # frozen_string_literal: true
2
+
3
+ module TraceViz
4
+ module Context
5
+ class Map
6
+ def initialize
7
+ @context_map = {}
8
+ end
9
+
10
+ def replace(new_map)
11
+ @context_map = new_map
12
+ end
13
+
14
+ def fetch(key)
15
+ @context_map.fetch(key)
16
+ rescue KeyError
17
+ raise ContextError, "Context for key '#{key}' not found"
18
+ end
19
+
20
+ def remove(*keys)
21
+ keys.each { |key| @context_map.delete(key) }
22
+ end
23
+
24
+ def reset
25
+ @context_map.clear
26
+ end
27
+ end
28
+ end
29
+ end
@@ -0,0 +1,37 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "trace_viz/context/config_context"
4
+ require "trace_viz/context/tracking_context"
5
+
6
+ module TraceViz
7
+ module Context
8
+ class Registry
9
+ CONTEXTS = {
10
+ config: ConfigContext,
11
+ tracking: TrackingContext,
12
+ }.freeze
13
+
14
+ class << self
15
+ # Builds a hash of context objects based on the provided contexts hash.
16
+ #
17
+ # @param [Hash] contexts A hash where the keys are context keys and the values are options for each context.
18
+ # Example:
19
+ # {
20
+ # context_key1: { option1: 'value1', option2: 'value2' },
21
+ # context_key2: { option1: 'value3', option2: 'value4' }
22
+ # }
23
+ #
24
+ # @return [Hash] A hash where the keys are context keys and the values are instantiated context objects.
25
+ #
26
+ # @raise [ArgumentError] If a context key is not found in the CONTEXTS hash.
27
+ def build(contexts)
28
+ contexts.each_with_object({}) do |(context_key, options), result|
29
+ klass = CONTEXTS.fetch(context_key)
30
+
31
+ result[context_key] = klass.new(**(options || {}))
32
+ end
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,37 @@
1
+ # frozen_string_literal: true
2
+
3
+ module TraceViz
4
+ module Context
5
+ module Tracking
6
+ class ActiveCalls
7
+ def initialize
8
+ @stack = []
9
+ end
10
+
11
+ def push(trace_data)
12
+ @stack.push(trace_data)
13
+ end
14
+
15
+ def pop
16
+ @stack.pop
17
+ end
18
+
19
+ def current
20
+ @stack.last
21
+ end
22
+
23
+ def empty?
24
+ @stack.empty?
25
+ end
26
+
27
+ def size
28
+ @stack.size
29
+ end
30
+
31
+ def clear
32
+ @stack.clear
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
@@ -2,16 +2,21 @@
2
2
 
3
3
  require "trace_viz/context/base_context"
4
4
  require "trace_viz/context/tracking/depth"
5
+ require "trace_viz/context/tracking/active_calls"
5
6
 
6
7
  module TraceViz
7
8
  module Context
8
9
  class TrackingContext < BaseContext
9
- attr_reader :depth
10
+ attr_reader :active_calls
10
11
 
11
12
  def initialize(**options)
12
13
  super
13
14
 
14
- @depth = Tracking::Depth.new
15
+ @active_calls = Tracking::ActiveCalls.new
16
+ end
17
+
18
+ def current_depth
19
+ active_calls.size
15
20
  end
16
21
  end
17
22
  end
@@ -5,8 +5,8 @@ require "trace_viz/context/manager"
5
5
  module TraceViz
6
6
  module Context
7
7
  class << self
8
- def for(type)
9
- Manager.get_context(type)
8
+ def for(key)
9
+ Manager.fetch_context(key)
10
10
  end
11
11
  end
12
12
  end
@@ -1,5 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require "trace_viz/defaults"
3
4
  require "trace_viz/logger"
4
5
  require "trace_viz/context"
5
6
  require "trace_viz/configuration"
@@ -0,0 +1,139 @@
1
+ # frozen_string_literal: true
2
+
3
+ module TraceViz
4
+ class Defaults
5
+ COLORS = {
6
+ reset: "\e[0m",
7
+ bold: "\e[1m",
8
+ dim: "\e[2m",
9
+ underline: "\e[4m",
10
+ reverse: "\e[7m",
11
+ black: "\e[30m",
12
+ red: "\e[31m",
13
+ green: "\e[32m",
14
+ yellow: "\e[33m",
15
+ blue: "\e[34m",
16
+ magenta: "\e[35m",
17
+ cyan: "\e[36m",
18
+ light_gray: "\e[37m",
19
+ dark_gray: "\e[90m",
20
+ light_red: "\e[91m",
21
+ light_green: "\e[92m",
22
+ light_yellow: "\e[93m",
23
+ light_blue: "\e[94m",
24
+ light_magenta: "\e[95m",
25
+ light_cyan: "\e[96m",
26
+ white: "\e[97m",
27
+ dim_light_gray: "\e[2;37m",
28
+ }.freeze
29
+
30
+ ACTION_EMOJIS = {
31
+ default: "",
32
+ info: "ℹ️",
33
+ success: "✅",
34
+ error: "❌",
35
+ warn: "⚠️",
36
+ start: "🚀",
37
+ processing: "🔄",
38
+ finish: "🏁",
39
+ exported: "📤",
40
+ skipped: "⏩",
41
+ stats: "📊",
42
+ }.freeze
43
+
44
+ ACTION_COLORS = {
45
+ default: :reset,
46
+ info: :cyan,
47
+ success: :green,
48
+ error: :light_red,
49
+ warn: :yellow,
50
+ start: :light_cyan,
51
+ processing: :dim_light_gray,
52
+ finish: :light_magenta,
53
+ exported: :light_green,
54
+ skipped: :dark_gray,
55
+ stats: :underline,
56
+ }.freeze
57
+
58
+ CONFIG = {
59
+ general: {
60
+ tab_size: 2,
61
+ show_indent: true,
62
+ show_depth: true,
63
+ max_display_depth: 3,
64
+ show_method_name: true,
65
+ },
66
+ source_location: {
67
+ show: false,
68
+ truncate_length: 100,
69
+ },
70
+ params: {
71
+ show: true,
72
+ mode: :name_and_value,
73
+ truncate_values: 50,
74
+ },
75
+ result: {
76
+ show: true,
77
+ truncate_length: 50,
78
+ },
79
+ execution: {
80
+ show_time: true,
81
+ show_trace_events: [:call, :return],
82
+ },
83
+ filters: [
84
+ :exclude_internal_call,
85
+ # :exclude_default_classes,
86
+ # :exclude_rails_framework,
87
+ # include_classes: {
88
+ # classes: [],
89
+ # },
90
+ # exclude_classes: {
91
+ # classes: [],
92
+ # },
93
+ # include_gems: {
94
+ # app_running: true,
95
+ # app_path: Dir.pwd,
96
+ # gems: [],
97
+ # },
98
+ # exclude_gems: {
99
+ # gems: [],
100
+ # },
101
+ ],
102
+ export: {
103
+ enabled: true,
104
+ path: "tmp",
105
+ format: :txt,
106
+ overwrite: false,
107
+ },
108
+ }.freeze
109
+
110
+ VALID_PARAM_MODES = [:name_and_value, :name_only, :value_only].freeze
111
+ VALID_EXPORT_FORMATS = [:txt, :json, :yml].freeze
112
+
113
+ class << self
114
+ def colors
115
+ COLORS
116
+ end
117
+
118
+ def action_colors
119
+ ACTION_COLORS
120
+ end
121
+
122
+ def action_emojis
123
+ ACTION_EMOJIS
124
+ end
125
+
126
+ def fetch_defaults
127
+ CONFIG.dup
128
+ end
129
+
130
+ def valid_param_modes
131
+ VALID_PARAM_MODES
132
+ end
133
+
134
+ def valid_export_formats
135
+ VALID_EXPORT_FORMATS
136
+ end
137
+ end
138
+ end
139
+ end
@@ -0,0 +1,84 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "fileutils"
4
+
5
+ require "trace_viz/context"
6
+ require_relative "transformers/text_transformer"
7
+
8
+ module TraceViz
9
+ module Exporters
10
+ class BaseExporter
11
+ def initialize(collector)
12
+ @config = Context.for(:config).configuration
13
+ @export_config = config.export
14
+ @logger = config.logger
15
+ @data = transform_collector_data(collector)
16
+ end
17
+
18
+ def export
19
+ unless export_enabled?
20
+ logger.warn("Export is disabled in configuration. Skipping export process.")
21
+ return
22
+ end
23
+
24
+ ensure_directory_exists
25
+ return if handle_empty_content == :skip
26
+ return if handle_existing_file == :skip
27
+
28
+ write_file(content)
29
+
30
+ logger.exported("Data successfully exported to #{file_path}")
31
+ end
32
+
33
+ private
34
+
35
+ attr_reader :config, :export_config, :logger, :data
36
+
37
+ def transform_collector_data(collector)
38
+ transformer = Transformers::TextTransformer.new(collector)
39
+ transformer.transform
40
+ end
41
+
42
+ def content
43
+ raise NotImplementedError
44
+ end
45
+
46
+ def export_enabled?
47
+ export_config[:enabled]
48
+ end
49
+
50
+ def ensure_directory_exists
51
+ FileUtils.mkdir_p(File.dirname(file_path))
52
+ end
53
+
54
+ def handle_existing_file
55
+ return unless File.exist?(file_path)
56
+
57
+ if export_config[:overwrite]
58
+ logger.processing("Overwriting existing file: #{file_path}")
59
+ else
60
+ logger.skipped("File already exists and overwrite is disabled: #{file_path}. Export skipped.")
61
+ :skip
62
+ end
63
+ end
64
+
65
+ def handle_empty_content
66
+ if content.nil? || content.strip.empty?
67
+ logger.skipped("Export content is empty. Export skipped.")
68
+ :skip
69
+ end
70
+ end
71
+
72
+ def file_path
73
+ format = export_config[:format]
74
+ path = export_config[:path]
75
+
76
+ "#{path}/trace_output.#{format}"
77
+ end
78
+
79
+ def write_file(data)
80
+ File.write(file_path, data)
81
+ end
82
+ end
83
+ end
84
+ end
@@ -0,0 +1,12 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "trace_viz/formatters/base_formatter"
4
+
5
+ module TraceViz
6
+ module Exporters
7
+ module Formatters
8
+ class BaseFormatter < TraceViz::Formatters::BaseFormatter
9
+ end
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,21 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "base_formatter"
4
+
5
+ module TraceViz
6
+ module Exporters
7
+ module Formatters
8
+ class MethodCallFormatter < BaseFormatter
9
+ def format
10
+ [
11
+ indent_representation,
12
+ depth_representation,
13
+ method_name_representation,
14
+ source_location_representation,
15
+ params_representation,
16
+ ].compact.join(" ")
17
+ end
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,22 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "base_formatter"
4
+
5
+ module TraceViz
6
+ module Exporters
7
+ module Formatters
8
+ class MethodReturnFormatter < BaseFormatter
9
+ def format
10
+ [
11
+ indent_representation,
12
+ depth_representation,
13
+ method_name_representation,
14
+ result_representation,
15
+ source_location_representation,
16
+ execution_time_representation,
17
+ ].compact.join(" ")
18
+ end
19
+ end
20
+ end
21
+ end
22
+ end