diff --git a/webapp/crashstats/crashstats/tests/test_utils.py b/webapp/crashstats/crashstats/tests/test_utils.py index 47fe3e7fa1..b861fdb04e 100644 --- a/webapp/crashstats/crashstats/tests/test_utils.py +++ b/webapp/crashstats/crashstats/tests/test_utils.py @@ -38,7 +38,58 @@ }, ), ( - # Now with a file that has VCS info but isn't in vcs_mappings. + # Test that firefox source files link to searchfox rather than the + # github.com repo they came from. + { + "frame": 0, + "module": "xul.dll", + "function": "Func", + "file": ( + "git:github.com/mozilla-firefox/firefox" + ":dom/base/StructuredCloneBlob.cpp" + ":ed6cfb3b73cb602ed2b8a75b1721c95b8e820322" + ), + "line": 253, + }, + { + "function": "Func", + "short_signature": "Func", + "line": 253, + "source_link": ( + "https://searchfox.org/firefox-main/rev" + "/ed6cfb3b73cb602ed2b8a75b1721c95b8e820322" + "/dom/base/StructuredCloneBlob.cpp#253" + ), + "file": "dom/base/StructuredCloneBlob.cpp", + "frame": 0, + "signature": "Func", + "module": "xul.dll", + }, + ), + ( + # Test that other github.com repos still link to github.com. + { + "frame": 0, + "module": "bad.dll", + "function": "Func", + "file": "git:github.com/some/project:dname/fname:rev", + "line": 576, + }, + { + "function": "Func", + "short_signature": "Func", + "line": 576, + "source_link": ( + "https://github.com/some/project/blob/rev/dname/fname#L576" + ), + "file": "dname/fname", + "frame": 0, + "signature": "Func", + "module": "bad.dll", + }, + ), + ( + # Now with a file whose server has no entry in vcs_mappings. { "frame": 0, "module": "bad.dll", @@ -140,7 +191,15 @@ def test_enhance_frame(data, expected): "hg.m.org": ( "http://hg.m.org/%(repo)s/file/%(revision)s/%(file)s#l%(line)s" ) - } + }, + "git": { + "github.com/mozilla-firefox/firefox": ( + "https://searchfox.org/firefox-main/rev/%(revision)s/%(file)s#%(line)s" + ), + "github.com": ( + "https://github.com/%(repo)s/blob/%(revision)s/%(file)s#L%(line)s" + ), + }, } # NOTE(willkg): data is modified in-place @@ -180,7 +239,8 @@ def test_enhance_frame_s3_generated_sources(): utils.enhance_frame(frame, {}) # Because it can't find a mapping in 'vcs_mappings', the frame's # 'file', the default behavior is to extract just the file's basename. - frame["file"] = "PCompositorBridgeChild.cpp" + assert frame["file"] == "PCompositorBridgeChild.cpp" + assert "source_link" not in frame # Try again, now with 's3' in vcs_mappings. frame = copy.copy(original_frame) diff --git a/webapp/crashstats/crashstats/utils.py b/webapp/crashstats/crashstats/utils.py index 869e903e03..137ec3ddd6 100644 --- a/webapp/crashstats/crashstats/utils.py +++ b/webapp/crashstats/crashstats/utils.py @@ -326,19 +326,23 @@ def enhance_frame(frame, vcs_mappings): # Leave it as is if it's not unweildly long. vcs_source_file_display = vcs_source_file - if vcstype in vcs_mappings: - if server in vcs_mappings[vcstype]: - link = vcs_mappings[vcstype][server] - frame["file"] = vcs_source_file_display - frame["source_link"] = link % { - "repo": repo, - "file": vcs_source_file, - "revision": revision, - "line": frame["line"], - } + mappings = vcs_mappings.get(vcstype, {}) + # Prefer a mapping for the specific repository (e.g. + # "github.com/mozilla-firefox/firefox") over one for the whole + # server (e.g. "github.com") + link = mappings.get(root) or mappings.get(server) + if link: + frame["file"] = vcs_source_file_display + frame["source_link"] = link % { + "repo": repo, + "file": vcs_source_file, + "revision": revision, + "line": frame["line"], + } else: - path_parts = vcs_source_file.split("/") - frame["file"] = path_parts.pop() + # Without a mapping there's nothing to link to, so just show the + # file's basename + frame["file"] = vcs_source_file.split("/")[-1] def enhance_json_dump(dump, vcs_mappings): diff --git a/webapp/crashstats/settings/base.py b/webapp/crashstats/settings/base.py index 572e853740..2f03ce42dd 100644 --- a/webapp/crashstats/settings/base.py +++ b/webapp/crashstats/settings/base.py @@ -302,6 +302,14 @@ def filter(self, record): "git.mozilla.org": ( "http://git.mozilla.org/?p=%(repo)s;a=blob;f=%(file)s;h=%(revision)s#l%(line)s" # noqa ), + # Firefox source links go to searchfox rather than GitHub. Searchfox + # serves the source for any revision in the mozilla-firefox/firefox + # repository from any of its firefox-* trees, since those trees share a + # single clone which has all the release branches. That means the + # "firefox-main" tree works for beta, release and esr revisions too. + "github.com/mozilla-firefox/firefox": ( + "https://searchfox.org/firefox-main/rev/%(revision)s/%(file)s#%(line)s" + ), "github.com": ( "https://github.com/%(repo)s/blob/%(revision)s/%(file)s#L%(line)s" ),