Skip to content

Commit 72d2aed

Browse files
committed
feat: Mirror test folder structure
AppMaps recorded from rspec and minitest are written to sub-folders of appmap_dir. The sub-folders mirror the test directories. This behavior can be disabled with APPMAP_MIRROR_TEST_FOLDERS=false
1 parent 577adcc commit 72d2aed

7 files changed

Lines changed: 29 additions & 14 deletions

File tree

lib/appmap/cucumber.rb

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ def write_scenario(scenario, appmap)
5252
appmap['metadata'] = update_metadata(scenario, appmap['metadata'])
5353
scenario_filename = AppMap::Util.scenario_filename(appmap['metadata']['name'])
5454

55-
AppMap::Util.write_appmap(File.join(APPMAP_OUTPUT_DIR, scenario_filename), appmap)
55+
AppMap::Util.write_appmap(APPMAP_OUTPUT_DIR, scenario_filename, appmap, source_location: scenario.location.to_s)
5656
end
5757

5858
def enabled?
@@ -85,6 +85,7 @@ def update_metadata(scenario, base_metadata)
8585
m['name'] = attributes.name
8686
m['feature'] = attributes.feature
8787
m['feature_group'] = attributes.feature_group
88+
m['source_location'] = scenario.location.to_s
8889
m['labels'] ||= []
8990
m['labels'] += (scenario.tags&.map(&:name) || [])
9091
m['frameworks'] ||= []

lib/appmap/minitest.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -128,7 +128,7 @@ def save(name:, class_map:, source_location:, test_status:, test_failure:, excep
128128
}.compact
129129
fname = AppMap::Util.scenario_filename(name)
130130

131-
AppMap::Util.write_appmap(File.join(APPMAP_OUTPUT_DIR, fname), appmap)
131+
AppMap::Util.write_appmap(APPMAP_OUTPUT_DIR, fname, appmap, source_location: source_location)
132132
end
133133

134134
def enabled?

lib/appmap/record.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,5 +24,5 @@
2424
'classMap' => AppMap.class_map(tracer.event_methods),
2525
'events' => events
2626
}
27-
AppMap::Util.write_appmap('appmap.json', appmap)
27+
AppMap::Util.write_appmap('.', 'appmap.json', appmap)
2828
end

lib/appmap/rspec.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -221,7 +221,7 @@ def save(name:, class_map:, source_location:, test_status:, test_failure:, excep
221221
}.compact
222222
fname = AppMap::Util.scenario_filename(name)
223223

224-
AppMap::Util.write_appmap(File.join(APPMAP_OUTPUT_DIR, fname), appmap)
224+
AppMap::Util.write_appmap(APPMAP_OUTPUT_DIR, fname, appmap, source_location: source_location)
225225
end
226226

227227
def enabled?

lib/appmap/util.rb

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -177,18 +177,32 @@ def swaggerize_path(path)
177177
end.join('/')
178178
end
179179

180+
def mirror_test_folders?
181+
ENV['APPMAP_MIRROR_TEST_FOLDERS'] != 'false'
182+
end
183+
180184
# Atomically writes AppMap data to +filename+.
181-
def write_appmap(filename, appmap)
185+
def write_appmap(output_dir, filename, appmap, source_location: nil)
182186
require 'tmpdir'
183187

188+
path_tokens = [ output_dir ]
189+
if source_location && mirror_test_folders?
190+
source_path, _ = source_location.split(':', 2)[0]
191+
source_dir = Array(Pathname.new(source_path).dirname.each_filename)[1..-1].join('/')
192+
path_tokens.push(source_dir) unless source_dir == ''
193+
end
194+
path_tokens.push(filename)
195+
appmap_path = File.join(*path_tokens)
196+
184197
# This is what Ruby Tempfile does; but we don't want the file to be unlinked.
185198
mode = File::RDWR | File::CREAT | File::EXCL
186199
::Dir::Tmpname.create([ 'appmap_', '.json' ]) do |tmpname|
187200
tempfile = File.open(tmpname, mode)
188201
tempfile.write(JSON.generate(appmap))
189202
tempfile.close
190203
# Atomically move the tempfile into place.
191-
FileUtils.mv tempfile.path, filename
204+
FileUtils.mkdir_p Pathname.new(appmap_path).dirname
205+
FileUtils.mv tempfile.path, appmap_path
192206
end
193207
end
194208

spec/rails_recording_spec.rb

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
include_context 'rails integration test setup'
77

88
describe 'rspec metadata' do
9-
let(:appmap_json_files) { Dir.glob("#{tmpdir}/appmap/rspec/*.appmap.json") }
9+
let(:appmap_json_files) { Dir.glob("#{tmpdir}/appmap/rspec/**/*.appmap.json") }
1010

1111
it 'appmap: false disables recording' do
1212
test_names = appmap_json_files.map(&File.method(:read)).map(&JSON.method(:parse)).map do |json|
@@ -20,7 +20,7 @@
2020
describe 'an API route' do
2121
describe 'creating an object' do
2222
let(:appmap_json_file) do
23-
'Api_UsersController_POST_api_users_with_required_parameters_creates_a_user.appmap.json'
23+
'controllers/Api_UsersController_POST_api_users_with_required_parameters_creates_a_user.appmap.json'
2424
end
2525

2626
it 'http_server_request is recorded in the appmap' do
@@ -104,7 +104,7 @@
104104
end
105105

106106
context 'with an object-style message' do
107-
let(:appmap_json_file) { 'Api_UsersController_POST_api_users_with_required_parameters_with_object-style_parameters_creates_a_user.appmap.json' }
107+
let(:appmap_json_file) { 'controllers/Api_UsersController_POST_api_users_with_required_parameters_with_object-style_parameters_creates_a_user.appmap.json' }
108108

109109
it 'message properties are recorded in the appmap' do
110110
expect(events).to include(
@@ -126,7 +126,7 @@
126126

127127
describe 'listing objects' do
128128
context 'with a custom header' do
129-
let(:appmap_json_file) { 'Api_UsersController_GET_api_users_with_a_custom_header_lists_the_users.appmap.json' }
129+
let(:appmap_json_file) { 'controllers/Api_UsersController_GET_api_users_with_a_custom_header_lists_the_users.appmap.json' }
130130

131131
it 'custom header is recorded in the appmap' do
132132
expect(events).to include(
@@ -144,7 +144,7 @@
144144
describe 'a UI route' do
145145
describe 'rendering a page using a template file' do
146146
let(:appmap_json_file) do
147-
'UsersController_GET_users_lists_the_users.appmap.json'
147+
'controllers/UsersController_GET_users_lists_the_users.appmap.json'
148148
end
149149

150150
it 'records the template file' do
@@ -186,7 +186,7 @@
186186

187187
describe 'rendering a page using a text template' do
188188
let(:appmap_json_file) do
189-
'UsersController_GET_users_login_shows_the_user.appmap.json'
189+
'controllers/UsersController_GET_users_login_shows_the_user.appmap.json'
190190
end
191191

192192
it 'records the normalized path info' do
@@ -257,7 +257,7 @@
257257
include_context 'rails integration test setup'
258258

259259
let(:appmap_json_file) do
260-
'Api_UsersController_POST_api_users_with_required_parameters_creates_a_user.appmap.json'
260+
'controllers/Api_UsersController_POST_api_users_with_required_parameters_creates_a_user.appmap.json'
261261
end
262262

263263
it 'http_server_request is recorded' do

spec/record_sql_rails_pg_spec.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ def run_specs(orm_module)
4949
'RAILS_ENV' => 'test'
5050
end
5151

52-
let(:appmap_json) { File.join tmpdir, "appmap/rspec/#{test_case}.appmap.json" }
52+
let(:appmap_json) { File.join tmpdir, "appmap/rspec/controllers/#{test_case}.appmap.json" }
5353
let(:appmap) { JSON.parse(File.read(appmap_json)) }
5454
let(:tmpdir) { app.tmpdir }
5555
let(:sql_events) { appmap['events'].select { |ev| ev.include? 'sql_query' } }

0 commit comments

Comments
 (0)