@@ -1673,62 +1673,65 @@ def map_paths_resource(
1673
1673
Map paths found in the ``to_resource`` extra_data to paths of the ``from_resources``
1674
1674
CodebaseResource queryset using the precomputed ``from_resources_index`` path index.
1675
1675
"""
1676
- relations = {}
1676
+ # Accumulate unique relation objects for bulk creation
1677
+ relations_to_create = {}
1677
1678
1678
1679
for map_type in map_types :
1679
- paths = to_resource .extra_data .get (map_type , [])
1680
- not_mapped_paths = to_resource .extra_data [f"{ map_type } _not_mapped" ] = []
1681
- process_relations (
1682
- to_resource ,
1683
- from_resources ,
1684
- from_resources_index ,
1685
- relations ,
1686
- map_type ,
1687
- paths ,
1688
- not_mapped_paths ,
1689
- )
1680
+ paths_in_binary = to_resource .extra_data .get (map_type , [])
1681
+ paths_not_mapped = to_resource .extra_data [f"{ map_type } _not_mapped" ] = []
1682
+ for item in process_paths_in_binary (
1683
+ to_resource = to_resource ,
1684
+ from_resources = from_resources ,
1685
+ from_resources_index = from_resources_index ,
1686
+ map_type = map_type ,
1687
+ paths_in_binary = paths_in_binary ,
1688
+ ):
1689
+ if isinstance (item , Path ):
1690
+ paths_not_mapped .append (item )
1691
+ else :
1692
+ rel_key , relation = item
1693
+ if rel_key not in relations_to_create :
1694
+ relations_to_create [rel_key ] = relation
1695
+ if paths_not_mapped :
1696
+ to_resource .save ()
1697
+ logger (
1698
+ f"WARNING: #{ len (paths_not_mapped )} { map_type } paths NOT mapped for: "
1699
+ f"{ to_resource .path !r} "
1700
+ )
1690
1701
1691
- if relations :
1692
- rels = CodebaseRelation .objects .bulk_create (relations .values ())
1702
+ if relations_to_create :
1703
+ rels = CodebaseRelation .objects .bulk_create (relations_to_create .values ())
1693
1704
logger (
1694
1705
f"Created { len (rels )} mappings using "
1695
- f"{ ', ' .join (map_types ). upper () } for: { to_resource .path !r} "
1706
+ f"{ ', ' .join (map_types )} for: { to_resource .path !r} "
1696
1707
)
1697
1708
else :
1698
1709
logger (
1699
- f"No mappings using { ', ' .join (map_types ).upper ()} for: "
1700
- f"{ to_resource .path !r} "
1710
+ f"No mappings using { ', ' .join (map_types )} for: " f"{ to_resource .path !r} "
1701
1711
)
1702
1712
1703
- for map_type in map_types :
1704
- if to_resource .extra_data .get (f"{ map_type } _not_mapped" ):
1705
- to_resource .save ()
1706
- logger (
1707
- f"WARNING: { map_type .upper ()} paths NOT mapped for: "
1708
- f"{ to_resource .path !r} : "
1709
- + ", " .join (map (repr , to_resource .extra_data [f"{ map_type } _not_mapped" ]))
1710
- )
1711
-
1712
1713
1713
- def process_relations (
1714
+ def process_paths_in_binary (
1714
1715
to_resource ,
1715
1716
from_resources ,
1716
1717
from_resources_index ,
1717
- relations ,
1718
1718
map_type ,
1719
- paths ,
1720
- not_mapped_paths ,
1719
+ paths_in_binary ,
1721
1720
):
1722
- """Process relations between resources."""
1723
- for path in paths :
1721
+ """
1722
+ Process list of paths in binary and Yield either:
1723
+ - a tuple of (unique key for a relationship, ``CodebaseRelation`` object)
1724
+ - Or a path if it was not mapped
1725
+ """
1726
+ for path in paths_in_binary :
1724
1727
match = pathmap .find_paths (path , from_resources_index )
1725
1728
if not match :
1726
- not_mapped_paths . append ( path )
1729
+ yield path
1727
1730
continue
1728
1731
1729
1732
matched_path_length = match .matched_path_length
1730
1733
if is_invalid_match (match , matched_path_length ):
1731
- not_mapped_paths . append ( path )
1734
+ yield path
1732
1735
continue
1733
1736
1734
1737
matched_from_resources = [
@@ -1744,15 +1747,14 @@ def process_relations(
1744
1747
}
1745
1748
1746
1749
rel_key = (winning_from_resource .path , to_resource .path , map_type )
1747
- if rel_key not in relations :
1748
- relation = CodebaseRelation (
1749
- project = winning_from_resource .project ,
1750
- from_resource = winning_from_resource ,
1751
- to_resource = to_resource ,
1752
- map_type = map_type ,
1753
- extra_data = extra_data ,
1754
- )
1755
- relations [rel_key ] = relation
1750
+ relation = CodebaseRelation (
1751
+ project = winning_from_resource .project ,
1752
+ from_resource = winning_from_resource ,
1753
+ to_resource = to_resource ,
1754
+ map_type = map_type ,
1755
+ extra_data = extra_data ,
1756
+ )
1757
+ yield rel_key , relation
1756
1758
1757
1759
1758
1760
def sort_matched_from_resources (matched_from_resources ):
@@ -1814,7 +1816,7 @@ def map_paths(project, file_type, collect_paths_func, map_types, logger=None):
1814
1816
1815
1817
1816
1818
def map_elfs (project , logger = None ):
1817
- """Map ELF file paths in a ``project``."""
1819
+ """Map ELF binaries to their sources in ``project``."""
1818
1820
from_resources = project .codebaseresources .files ().from_codebase ()
1819
1821
to_resources = (
1820
1822
project .codebaseresources .files ().to_codebase ().has_no_relation ().elfs ()
@@ -1877,7 +1879,7 @@ def get_go_file_paths(location):
1877
1879
1878
1880
1879
1881
def map_go_paths (project , logger = None ):
1880
- """Map Go file paths in a project."""
1882
+ """Map Go binaries to their source in `` project`` ."""
1881
1883
from_resources = project .codebaseresources .files ().from_codebase ()
1882
1884
to_resources = (
1883
1885
project .codebaseresources .files ()
0 commit comments