diff --git a/cachi2/core/package_managers/yarn_classic/main.py b/cachi2/core/package_managers/yarn_classic/main.py index 554d07814..5e6d37f0d 100644 --- a/cachi2/core/package_managers/yarn_classic/main.py +++ b/cachi2/core/package_managers/yarn_classic/main.py @@ -9,7 +9,6 @@ run_yarn_cmd, ) from cachi2.core.package_managers.yarn_classic.resolver import resolve_packages -from cachi2.core.package_managers.yarn_classic.workspaces import extract_workspace_metadata from cachi2.core.rooted_path import RootedPath log = logging.getLogger(__name__) @@ -29,11 +28,6 @@ def _ensure_mirror_dir_exists(output_dir: RootedPath) -> None: package_path = request.source_dir.join_within_root(package.path) _ensure_mirror_dir_exists(request.output_dir) _resolve_yarn_project(package_path, request.output_dir) - # Workspaces metadata is not used at the moment, but will - # eventualy be converted into components. Using a noop assertion - # to prevent linters from complaining. - workspaces = extract_workspace_metadata(package_path) - assert workspaces is not None # nosec -- see comment above return RequestOutput.from_obj_list( components, _generate_build_environment_variables(), project_files=[] diff --git a/cachi2/core/package_managers/yarn_classic/resolver.py b/cachi2/core/package_managers/yarn_classic/resolver.py index 4d3bc7a4c..b6b92ec00 100644 --- a/cachi2/core/package_managers/yarn_classic/resolver.py +++ b/cachi2/core/package_managers/yarn_classic/resolver.py @@ -11,6 +11,10 @@ from cachi2.core.errors import PackageRejected, UnexpectedFormat from cachi2.core.package_managers.npm import NPM_REGISTRY_CNAMES from cachi2.core.package_managers.yarn.project import PackageJson +from cachi2.core.package_managers.yarn_classic.workspaces import ( + Workspace, + extract_workspace_metadata, +) from cachi2.core.rooted_path import RootedPath # https://github.com/yarnpkg/yarn/blob/7cafa512a777048ce0b666080a24e80aae3d66a9/src/resolvers/exotics/git-resolver.js#L15-L17 @@ -211,6 +215,25 @@ def _get_main_package(source_dir: RootedPath) -> WorkspacePackage: ) +def _get_workspace_packages( + source_dir: RootedPath, workspaces: list[Workspace] +) -> list[WorkspacePackage]: + """Return a WorkspacePackage for each Workspace.""" + return [ + WorkspacePackage( + name=ws.package_contents["name"], + version=ws.package_contents.get("version"), + relpath=ws.path.relative_to(source_dir.path), + ) + for ws in workspaces + ] + + def resolve_packages(source_dir: RootedPath) -> Iterable[YarnClassicPackage]: """Return an iterable of Packages corresponding to all project dependencies.""" - return chain([_get_main_package(source_dir)], _get_packages_from_lockfile(source_dir)) + workspaces = extract_workspace_metadata(source_dir) + return chain( + [_get_main_package(source_dir)], + _get_workspace_packages(source_dir, workspaces), + _get_packages_from_lockfile(source_dir), + ) diff --git a/tests/unit/package_managers/yarn_classic/test_main.py b/tests/unit/package_managers/yarn_classic/test_main.py index 6e9897129..ecb757bc7 100644 --- a/tests/unit/package_managers/yarn_classic/test_main.py +++ b/tests/unit/package_managers/yarn_classic/test_main.py @@ -52,9 +52,7 @@ def test_generate_build_environment_variables( indirect=["input_request"], ) @mock.patch("cachi2.core.package_managers.yarn_classic.main._resolve_yarn_project") -@mock.patch("cachi2.core.package_managers.yarn_classic.main.extract_workspace_metadata") def test_fetch_yarn_source( - mock_extract_metadata: mock.Mock, mock_resolve_yarn: mock.Mock, input_request: Request, yarn_classic_env_variables: list[EnvironmentVariable], diff --git a/tests/unit/package_managers/yarn_classic/test_resolver.py b/tests/unit/package_managers/yarn_classic/test_resolver.py index 32a911dd3..e12bbdca6 100644 --- a/tests/unit/package_managers/yarn_classic/test_resolver.py +++ b/tests/unit/package_managers/yarn_classic/test_resolver.py @@ -17,12 +17,14 @@ YarnClassicPackage, _get_main_package, _get_packages_from_lockfile, + _get_workspace_packages, _is_from_npm_registry, _is_git_url, _is_tarball_url, _YarnClassicPackageFactory, resolve_packages, ) +from cachi2.core.package_managers.yarn_classic.workspaces import Workspace from cachi2.core.rooted_path import PathOutsideRoot, RootedPath VALID_GIT_URLS = [ @@ -257,22 +259,32 @@ def test__get_packages_from_lockfile( assert output == [mock_package_1, mock_package_2] +@mock.patch("cachi2.core.package_managers.yarn_classic.resolver._get_workspace_packages") +@mock.patch("cachi2.core.package_managers.yarn_classic.resolver.extract_workspace_metadata") @mock.patch("cachi2.core.package_managers.yarn_classic.resolver._get_packages_from_lockfile") @mock.patch("cachi2.core.package_managers.yarn_classic.resolver._get_main_package") def test_resolve_packages( mock_get_main_package: mock.Mock, mock_get_lockfile_packages: mock.Mock, + mock_extract_workspaces: mock.Mock, + mock_get_workspace_packages: mock.Mock, rooted_tmp_path: RootedPath, ) -> None: main_package = mock.Mock() + workspace_packages = [mock.Mock()] lockfile_packages = [mock.Mock(), mock.Mock()] - expected_output = [main_package, *lockfile_packages] + expected_output = [main_package, *workspace_packages, *lockfile_packages] mock_get_main_package.return_value = main_package mock_get_lockfile_packages.return_value = lockfile_packages + mock_get_workspace_packages.return_value = workspace_packages output = resolve_packages(rooted_tmp_path) + mock_extract_workspaces.assert_called_once_with(rooted_tmp_path) mock_get_main_package.assert_called_once_with(rooted_tmp_path) + mock_get_workspace_packages.assert_called_once_with( + rooted_tmp_path, mock_extract_workspaces.return_value + ) mock_get_lockfile_packages.assert_called_once_with(rooted_tmp_path) assert list(output) == expected_output @@ -308,3 +320,21 @@ def test__get_main_package_no_name( with pytest.raises(PackageRejected, match=error_msg): _get_main_package(rooted_tmp_path) + + +def test__get_workspace_packages(rooted_tmp_path: RootedPath) -> None: + workspace_path = rooted_tmp_path.join_within_root("foo").path + workspace = Workspace( + path=workspace_path, + package_contents={"name": "foo", "version": "1.0.0"}, + ) + expected = [ + WorkspacePackage( + name="foo", + version="1.0.0", + relpath=workspace_path.relative_to(rooted_tmp_path.path), + ) + ] + + output = _get_workspace_packages(rooted_tmp_path, [workspace]) + assert output == expected