Skip to content

Commit 75d6c9e

Browse files
authored
feat: perform basic mapping before normalizing mapping (#1999)
Signed-off-by: Chin Yeung Li <tli@nexb.com>
1 parent d500fde commit 75d6c9e

3 files changed

Lines changed: 38 additions & 4 deletions

File tree

scanpipe/pipes/d2d.py

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -170,12 +170,21 @@ def _map_jvm_to_class_resource(
170170
from/ fully qualified binary files.
171171
"""
172172
for extension in jvm_lang.source_extensions:
173-
normalized_path = jvm_lang.get_normalized_path(
173+
# Perform basic conversion from .class to source file path
174+
source_path = jvm_lang.get_source_path(
174175
path=to_resource.path, extension=extension
175176
)
176-
match = pathmap.find_paths(path=normalized_path, index=from_classes_index)
177+
# Perform basic mapping without normalization for scenarios listed in
178+
# https://github.com/aboutcode-org/scancode.io/issues/1873
179+
match = pathmap.find_paths(path=source_path, index=from_classes_index)
180+
177181
if not match:
178-
return
182+
normalized_path = jvm_lang.get_normalized_path(
183+
path=to_resource.path, extension=extension
184+
)
185+
match = pathmap.find_paths(path=normalized_path, index=from_classes_index)
186+
if not match:
187+
return
179188

180189
for resource_id in match.resource_ids:
181190
from_resource = from_resources.get(id=resource_id)

scanpipe/pipes/jvm.py

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -140,12 +140,27 @@ def get_normalized_path(cls, path, extension):
140140
# https://github.com/aboutcode-org/scancode.io/issues/1994
141141
if class_name.endswith("_$logger.class"):
142142
class_name, _, _ = class_name.partition("_$logger.class")
143-
elif "$" in class_name: # inner class
143+
elif "$" in class_name and not class_name.startswith("$"): # inner class
144144
class_name, _, _ = class_name.partition("$")
145145
else:
146146
class_name, _, _ = class_name.partition(".") # plain .class
147147
return str(path.parent / f"{class_name}{extension}")
148148

149+
@classmethod
150+
def get_source_path(cls, path, extension):
151+
"""
152+
Return a JVM file path for ``path`` .class file path string.
153+
No normalization is performed.
154+
"""
155+
if not path.endswith(cls.binary_extensions):
156+
raise ValueError(
157+
f"Only path ending with {cls.binary_extensions} are supported."
158+
)
159+
path = Path(path.strip("/"))
160+
class_name = path.name
161+
class_name, _, _ = class_name.partition(".") # plain .class
162+
return str(path.parent / f"{class_name}{extension}")
163+
149164

150165
def find_expression(lines, regex):
151166
"""

scanpipe/tests/pipes/test_jvm.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,16 @@ def test_scanpipe_pipes_jvm_get_java_package_too_far_down(self):
8484
package = jvm.JavaLanguage.get_source_package(input_location)
8585
self.assertIsNone(package)
8686

87+
def test_scanpipe_pipes_jvm_get_source_java_path(self):
88+
njp = jvm.JavaLanguage.get_source_path("foo/org/common/Bar.class", ".java")
89+
self.assertEqual("foo/org/common/Bar.java", njp)
90+
91+
def test_scanpipe_pipes_jvm_get_source_java_path_with_inner_class(self):
92+
njp = jvm.JavaLanguage.get_source_path(
93+
"foo/org/common/Bar$inner.class", ".java"
94+
)
95+
self.assertEqual("foo/org/common/Bar$inner.java", njp)
96+
8797
def test_scanpipe_pipes_jvm_get_normalized_java_path(self):
8898
njp = jvm.JavaLanguage.get_normalized_path("foo/org/common/Bar.class", ".java")
8999
self.assertEqual("foo/org/common/Bar.java", njp)

0 commit comments

Comments
 (0)