posthog-ruby 3.16.0 → 3.17.0

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: 1091ed7a7995e58f6abbf25b2a45dba44b9c2f15ff152b5a5bf4044856269161
4
- data.tar.gz: f5f5542aa6c66d00bb22c7362ff4e1613eee4ae20b94cf3fe04933ad798b83b5
3
+ metadata.gz: 187ed0ab3a49d0137a8a5516792d00eb6baf5242ed6665df879563656a6541ac
4
+ data.tar.gz: cf463f7135031a7d6975bac3eb72ad48ead37729c577738f80fe03e83a6c8f9c
5
5
  SHA512:
6
- metadata.gz: 8f9bc8bf1c98bce5faf4856db35779fd7436df5d538eeb5ae09c3715feb765ade37d22e903056a974f8942f1e207da6de0cba20cd1c08ee601db56a260b33ee3
7
- data.tar.gz: 201ed92c1b736ba97e9d76e3221f2297d9f49de0bdee9adc331991d4316db22bf6d014305ef182df6afcc7b1760b2eb7d3026d4337de81c9ce5dbec225239826
6
+ metadata.gz: 5f0906fded5049de9de8638ffee0345e7db4bee9a73387fcc602247a9e62193e011fa89358a1001d8818ec216116aec3750548e0c056a6488a7c3360784da038
7
+ data.tar.gz: 5d7c036bfccdb96b1343287a7349c5ab95ec7184b88db2189f9ba4d805756e050edc3f14533517b79a30377253649ceb1ccecf95a0f9950fdc28812cf18ec629
@@ -97,8 +97,10 @@ module PostHog
97
97
  def self.build_stacktrace(backtrace)
98
98
  return nil unless backtrace && !backtrace.empty?
99
99
 
100
+ root = project_root
101
+ roots = dependency_roots(root)
100
102
  frames = backtrace.first(50).map do |line|
101
- parse_backtrace_line(line)
103
+ parse_backtrace_line(line, project_root: root, dependency_roots: roots)
102
104
  end.compact.reverse
103
105
 
104
106
  {
@@ -108,8 +110,10 @@ module PostHog
108
110
  end
109
111
 
110
112
  # @param line [String]
113
+ # @param project_root [String, nil] Project root used to derive project-relative filenames.
114
+ # @param dependency_roots [Array<String>, nil] Cached gem and stdlib roots.
111
115
  # @return [Hash, nil]
112
- def self.parse_backtrace_line(line)
116
+ def self.parse_backtrace_line(line, project_root: self.project_root, dependency_roots: nil)
113
117
  match = line.match(RUBY_INPUT_FORMAT)
114
118
  return nil unless match
115
119
 
@@ -118,11 +122,11 @@ module PostHog
118
122
  method_name = match[5]
119
123
 
120
124
  frame = {
121
- 'filename' => File.basename(file),
125
+ 'filename' => frame_filename(file, project_root),
122
126
  'abs_path' => file,
123
127
  'lineno' => lineno,
124
128
  'function' => method_name,
125
- 'in_app' => !gem_path?(file),
129
+ 'in_app' => !gem_path?(file, dependency_roots || self.dependency_roots(project_root)),
126
130
  'platform' => 'ruby'
127
131
  }
128
132
 
@@ -131,13 +135,71 @@ module PostHog
131
135
  frame
132
136
  end
133
137
 
138
+ # Root directory the application runs from, used to derive stable
139
+ # project-relative filenames from per-host deploy paths
140
+ # (e.g. `/app/releases/20240101/...`).
141
+ #
142
+ # @return [String]
143
+ def self.project_root
144
+ if defined?(::Rails) && ::Rails.respond_to?(:root) && ::Rails.root
145
+ ::Rails.root.to_s
146
+ else
147
+ Dir.pwd
148
+ end
149
+ rescue StandardError
150
+ Dir.pwd
151
+ end
152
+
153
+ # Stable filename used for fingerprinting: the project-relative path when
154
+ # the file lives inside the project root, its basename otherwise. The raw
155
+ # absolute path is kept separately in `abs_path`.
156
+ #
157
+ # @param path [String]
158
+ # @param project_root [String, nil]
159
+ # @return [String]
160
+ def self.frame_filename(path, project_root)
161
+ if project_root && !project_root.empty? && path_within?(path, project_root)
162
+ relative = path[project_root.length..]
163
+ relative = relative[1..] while relative.start_with?(File::SEPARATOR)
164
+ return relative unless relative.empty?
165
+ end
166
+
167
+ File.basename(path)
168
+ end
169
+
170
+ # Whether the path belongs to an installed gem or the Ruby standard library,
171
+ # based on gem install locations rather than path substrings.
172
+ #
173
+ # @param path [String]
174
+ # @param dependency_roots [Array<String>]
175
+ # @return [Boolean]
176
+ def self.gem_path?(path, dependency_roots = self.dependency_roots)
177
+ dependency_roots.any? { |root| path_within?(path, root) }
178
+ end
179
+
180
+ # @param project_root [String]
181
+ # @return [Array<String>] Directories containing installed gems and the Ruby stdlib.
182
+ def self.dependency_roots(project_root = self.project_root)
183
+ roots = []
184
+ if defined?(Gem)
185
+ roots.concat(Gem.path) if Gem.respond_to?(:path)
186
+ roots << Gem.default_dir if Gem.respond_to?(:default_dir)
187
+ roots.concat(Gem.loaded_specs.each_value.map(&:full_gem_path)) if Gem.respond_to?(:loaded_specs)
188
+ end
189
+ roots << RbConfig::CONFIG['rubylibprefix'] if defined?(RbConfig)
190
+ # The project itself can be a loaded spec (e.g. a gem developed in place,
191
+ # or a Rails engine); its frames are still application code.
192
+ roots.compact.reject(&:empty?).uniq - [project_root]
193
+ rescue StandardError
194
+ []
195
+ end
196
+
134
197
  # @param path [String]
198
+ # @param root [String]
135
199
  # @return [Boolean]
136
- def self.gem_path?(path)
137
- path.include?('/gems/') ||
138
- path.include?('/ruby/') ||
139
- path.include?('/.rbenv/') ||
140
- path.include?('/.rvm/')
200
+ def self.path_within?(path, root)
201
+ root = root.chomp(File::SEPARATOR)
202
+ path == root || path.start_with?("#{root}#{File::SEPARATOR}")
141
203
  end
142
204
 
143
205
  # @param frame [Hash]
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module PostHog
4
- VERSION = '3.16.0'
4
+ VERSION = '3.17.0'
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: posthog-ruby
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.16.0
4
+ version: 3.17.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - ''