Assemble Cargo.toml and possible Cargo.lock datafiles. Also support cargo workspaces where we have multiple packages from a repository and some shared information present at top-level.
(cls, package_data, resource, codebase, package_adder)
| 49 | class CargoBaseHandler(models.DatafileHandler): |
| 50 | @classmethod |
| 51 | def assemble(cls, package_data, resource, codebase, package_adder): |
| 52 | """ |
| 53 | Assemble Cargo.toml and possible Cargo.lock datafiles. Also |
| 54 | support cargo workspaces where we have multiple packages from |
| 55 | a repository and some shared information present at top-level. |
| 56 | """ |
| 57 | workspace = package_data.extra_data.get('workspace', {}) |
| 58 | workspace_members = workspace.get("members", []) |
| 59 | workspace_package_data = workspace.get("package", {}) |
| 60 | attributes_to_copy = [ |
| 61 | "license_detections", |
| 62 | "declared_license_expression", |
| 63 | "declared_license_expression_spdx" |
| 64 | ] |
| 65 | if "license" in workspace_package_data: |
| 66 | for attribute in attributes_to_copy: |
| 67 | package_data.extra_data[attribute] = 'workspace' |
| 68 | workspace_package_data[attribute] = getattr(package_data, attribute) |
| 69 | |
| 70 | workspace_root = resource.parent(codebase) |
| 71 | if not workspace_root: |
| 72 | # If there's no parent (e.g., scanning a single file), use the directory part of the resource path |
| 73 | workspace_root_path = os.path.dirname(resource.path) |
| 74 | else: |
| 75 | workspace_root_path = workspace_root.path |
| 76 | |
| 77 | if workspace_package_data and workspace_members: |
| 78 | |
| 79 | # TODO: support glob patterns found in cargo workspaces |
| 80 | for workspace_member_path in workspace_members: |
| 81 | workspace_directory_path = os.path.join(workspace_root_path, workspace_member_path) |
| 82 | workspace_directory = codebase.get_resource(path=workspace_directory_path) |
| 83 | if not workspace_directory: |
| 84 | continue |
| 85 | |
| 86 | # Update the package data for all members with the |
| 87 | # workspace package data |
| 88 | for resource in workspace_directory.children(codebase): |
| 89 | if cls.is_datafile(location=resource.location): |
| 90 | if not resource.package_data: |
| 91 | continue |
| 92 | |
| 93 | if TRACE: |
| 94 | logger_debug(f"Resource manifest to update: {resource.path}") |
| 95 | |
| 96 | updated_package_data = cls.update_resource_package_data( |
| 97 | workspace=workspace, |
| 98 | workspace_package_data=workspace_package_data, |
| 99 | resource_package_data=resource.package_data.pop(), |
| 100 | mapping=CARGO_ATTRIBUTE_MAPPING, |
| 101 | ) |
| 102 | resource.package_data.append(updated_package_data) |
| 103 | resource.save(codebase) |
| 104 | |
| 105 | yield from cls.assemble_from_many_datafiles( |
| 106 | datafile_name_patterns=('Cargo.toml', 'cargo.toml', 'Cargo.lock', 'cargo.lock'), |
| 107 | directory=workspace_directory, |
| 108 | codebase=codebase, |
nothing calls this directly
no test coverage detected