From 4f21e4e743d4c9f85d25d925ca385577288fcf77 Mon Sep 17 00:00:00 2001 From: Workshop Date: Wed, 8 Jul 2026 13:27:42 -0400 Subject: [PATCH 1/6] feat: opt into git-driven build root via CHARMCRAFT_EXPERIMENTAL_MONOREPO When CHARMCRAFT_EXPERIMENTAL_MONOREPO is set to a truthy value, charmcraft passes use_git_build_root=True to craft-application, which mounts the git repository root as the build root. This enables charms in a monorepo to access shared local dependencies (e.g. ../common) during pack. CHARMCRAFT-710 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --- charmcraft/application/main.py | 3 +++ charmcraft/const.py | 1 + 2 files changed, 4 insertions(+) diff --git a/charmcraft/application/main.py b/charmcraft/application/main.py index 63e634759..5a5c0eb38 100644 --- a/charmcraft/application/main.py +++ b/charmcraft/application/main.py @@ -48,6 +48,9 @@ docs_url="https://documentation.ubuntu.com/charmcraft/{version}", supports_multi_base=True, mandatory_adoptable_fields=[], # Version field is not mandatory. + use_git_build_root=util.strtobool( + os.getenv(const.EXPERIMENTAL_MONOREPO_ENV_VAR, "false") + ), ) PRIME_BEHAVIOUR_CHANGE_MESSAGE = ( diff --git a/charmcraft/const.py b/charmcraft/const.py index 20dd29562..2dd61c2b8 100644 --- a/charmcraft/const.py +++ b/charmcraft/const.py @@ -26,6 +26,7 @@ ALTERNATE_AUTH_ENV_VAR = "CHARMCRAFT_AUTH" DEVELOPER_MODE_ENV_VAR = "CHARMCRAFT_DEVELOPER" EXPERIMENTAL_EXTENSIONS_ENV_VAR = "CHARMCRAFT_ENABLE_EXPERIMENTAL_EXTENSIONS" +EXPERIMENTAL_MONOREPO_ENV_VAR = "CHARMCRAFT_EXPERIMENTAL_MONOREPO" IMAGE_INFO_ENV_VAR = "CHARMCRAFT_IMAGE_INFO" PROVIDER_ENV_VAR = "CHARMCRAFT_PROVIDER" SHARED_CACHE_ENV_VAR = "CRAFT_SHARED_CACHE" From 4d6bd78402066139d8a6e26b8cf166edbed13616 Mon Sep 17 00:00:00 2001 From: Workshop Date: Wed, 8 Jul 2026 13:27:47 -0400 Subject: [PATCH 2/6] fix(plugins): use part_build_subdir for charm source copy When a charm uses a source-subdir (as happens with root_dir/monorepo builds), the charm files live at part_build_subdir not part_build_dir. Fix get_charm_copy_commands in all three charm plugins (poetry, python, uv) to use part_build_subdir so that src/, lib/ etc. are found correctly. CHARMCRAFT-710 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --- charmcraft/parts/plugins/_poetry.py | 2 +- charmcraft/parts/plugins/_python.py | 2 +- charmcraft/parts/plugins/_uv.py | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/charmcraft/parts/plugins/_poetry.py b/charmcraft/parts/plugins/_poetry.py index b0c5b5cdc..c718fc417 100644 --- a/charmcraft/parts/plugins/_poetry.py +++ b/charmcraft/parts/plugins/_poetry.py @@ -76,7 +76,7 @@ def _get_package_install_commands(self) -> list[str]: return [ *super()._get_package_install_commands(), *utils.get_charm_copy_commands( - self._part_info.part_build_dir, self._part_info.part_install_dir + self._part_info.part_build_subdir, self._part_info.part_install_dir ), ] diff --git a/charmcraft/parts/plugins/_python.py b/charmcraft/parts/plugins/_python.py index 1123dd4e3..280df9f08 100644 --- a/charmcraft/parts/plugins/_python.py +++ b/charmcraft/parts/plugins/_python.py @@ -79,7 +79,7 @@ def _get_package_install_commands(self) -> list[str]: f"{pip} install --no-deps {install_params}", f"{pip} check", *utils.get_charm_copy_commands( - self._part_info.part_build_dir, self._part_info.part_install_dir + self._part_info.part_build_subdir, self._part_info.part_install_dir ), ] diff --git a/charmcraft/parts/plugins/_uv.py b/charmcraft/parts/plugins/_uv.py index b2bcfe318..409d2fd32 100644 --- a/charmcraft/parts/plugins/_uv.py +++ b/charmcraft/parts/plugins/_uv.py @@ -48,7 +48,7 @@ def _get_package_install_commands(self) -> list[str]: return [ *orig_cmds, *utils.get_charm_copy_commands( - self._part_info.part_build_dir, self._part_info.part_install_dir + self._part_info.part_build_subdir, self._part_info.part_install_dir ), ] From f4e18e4373c666ef3029343195404aa0d6a44c91 Mon Sep 17 00:00:00 2001 From: Workshop Date: Wed, 8 Jul 2026 13:27:53 -0400 Subject: [PATCH 3/6] test(spread): add monorepo spread tests for CHARMCRAFT-710 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Move microk8s setup out of the charms/ suite-level prepare and into k8s-operator/task.yaml (the only test that uses a k8s Juju controller) so monorepo tests don't require microk8s. - Add tests/spread/charms/monorepo/ with four variants covering mysql-operators and mysql-router-operators × machines + kubernetes. - Add tests/spread/commands/git-build-root/ as a lightweight unit-level smoke test for the feature flag. CHARMCRAFT-710 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --- spread.yaml | 9 --- tests/spread/charms/k8s-operator/task.yaml | 8 +++ tests/spread/charms/monorepo/task.yaml | 39 ++++++++++++ .../spread/commands/git-build-root/task.yaml | 62 +++++++++++++++++++ 4 files changed, 109 insertions(+), 9 deletions(-) create mode 100644 tests/spread/charms/monorepo/task.yaml create mode 100644 tests/spread/commands/git-build-root/task.yaml diff --git a/spread.yaml b/spread.yaml index 0bc27741a..0bc0a6116 100644 --- a/spread.yaml +++ b/spread.yaml @@ -236,17 +236,8 @@ suites: summary: real charm building tests prepare: | snap install juju --channel=3/stable - snap install microk8s --channel=1.28-strict/stable - # Set up Juju controllers for the charms lxc network set lxdbr0 ipv6.address none mkdir -p ~/.local/share # Workaround for Juju not being able to create the directory - microk8s enable hostpath-storage - microk8s enable dns - snap alias microk8s.kubectl kubectl - - if ! juju controllers | grep -q k8s; then - juju bootstrap microk8s k8s - fi if ! juju controllers | grep -q lxd; then juju bootstrap localhost lxd fi diff --git a/tests/spread/charms/k8s-operator/task.yaml b/tests/spread/charms/k8s-operator/task.yaml index adf11bbf6..d404549eb 100644 --- a/tests/spread/charms/k8s-operator/task.yaml +++ b/tests/spread/charms/k8s-operator/task.yaml @@ -31,6 +31,14 @@ environment: JUJU_MODEL: k8s-operator-test prepare: | + snap install microk8s --channel=1.28-strict/stable + microk8s enable hostpath-storage + microk8s enable dns + snap alias microk8s.kubectl kubectl + if ! juju controllers | grep -q k8s; then + juju bootstrap microk8s k8s + fi + git clone --depth=1 "${CHARM}" charm restore: | diff --git a/tests/spread/charms/monorepo/task.yaml b/tests/spread/charms/monorepo/task.yaml new file mode 100644 index 000000000..870e243f8 --- /dev/null +++ b/tests/spread/charms/monorepo/task.yaml @@ -0,0 +1,39 @@ +summary: Pack a charm from a monorepo using CHARMCRAFT_EXPERIMENTAL_MONOREPO + +systems: + - ubuntu-26.04-64 + +kill-timeout: 60m + +environment: + CHARMCRAFT_EXPERIMENTAL_MONOREPO: "1" + REPO/mysql_operators_machines: mysql-operators + CHARM_SUBDIR/mysql_operators_machines: machines + REPO/mysql_operators_kubernetes: mysql-operators + CHARM_SUBDIR/mysql_operators_kubernetes: kubernetes + REPO/mysql_router_operators_machines: mysql-router-operators + CHARM_SUBDIR/mysql_router_operators_machines: machines + REPO/mysql_router_operators_kubernetes: mysql-router-operators + CHARM_SUBDIR/mysql_router_operators_kubernetes: kubernetes + +prepare: | + git clone --depth=1 https://github.com/canonical/"${REPO}".git /tmp/"${REPO}" + python3 - << 'EOF' + import os, yaml, pathlib + p = pathlib.Path(f'/tmp/{os.environ["REPO"]}/{os.environ["CHARM_SUBDIR"]}/charmcraft.yaml') + d = yaml.safe_load(p.read_text()) + d["parts"].pop("files", None) + d["parts"].get("charm-poetry", {}).pop("override-build", None) + p.write_text(yaml.dump(d)) + EOF + +restore: | + cd /tmp/"${REPO}"/"${CHARM_SUBDIR}" 2>/dev/null && charmcraft clean || true + rm -rf /tmp/"${REPO}" + +execute: | + cd /tmp/"${REPO}"/"${CHARM_SUBDIR}" + charmcraft pack + CHARM_FILE=$(ls *_ubuntu@26.04-amd64.charm | head -1) + unzip -l "${CHARM_FILE}" | MATCH "src/charm.py" + unzip -l "${CHARM_FILE}" | MATCH "venv/lib/python.*/site-packages/ops/" diff --git a/tests/spread/commands/git-build-root/task.yaml b/tests/spread/commands/git-build-root/task.yaml new file mode 100644 index 000000000..bc1f6f19d --- /dev/null +++ b/tests/spread/commands/git-build-root/task.yaml @@ -0,0 +1,62 @@ +summary: Pack a charm from a monorepo using CHARMCRAFT_EXPERIMENTAL_MONOREPO + +# Ubuntu 18.04 times out during global prepare (snap installs too slow). +systems: + - ubuntu-20.04-64 + - ubuntu-22.04-64 + - ubuntu-24.04-64 + - ubuntu-25.10-64 + - ubuntu-26.04-64 + +kill-timeout: 30m + +environment: + CHARMCRAFT_EXPERIMENTAL_MONOREPO: "1" + +execute: | + . /etc/os-release + + mkdir -p /tmp/monorepo/shared/mylib + mkdir -p /tmp/monorepo/charm + git -C /tmp/monorepo init + git -C /tmp/monorepo config user.email "test@example.com" + git -C /tmp/monorepo config user.name "Test" + + echo "GREETING = 'hello from shared library'" > /tmp/monorepo/shared/mylib/__init__.py + + cat > /tmp/monorepo/charm/charmcraft.yaml << EOF + name: monorepo-test-charm + type: charm + title: Monorepo test charm + summary: Tests git-driven build root monorepo support. + description: Verifies that CHARMCRAFT_EXPERIMENTAL_MONOREPO mounts the git root. + base: ubuntu@${VERSION_ID} + build-base: ubuntu@${VERSION_ID} + platforms: + amd64: + parts: + charm: + plugin: dump + source: . + shared-lib: + plugin: dump + source: ../shared + organize: + "*": shared/ + EOF + + cd /tmp/monorepo/charm + charmcraft pack + + arch=$(dpkg --print-architecture) + artifact=/tmp/monorepo/charm/monorepo-test-charm_${arch}.charm + test -f "${artifact}" + + mkdir /tmp/monorepo/unpacked + unzip -q "${artifact}" -d /tmp/monorepo/unpacked + test -f /tmp/monorepo/unpacked/shared/mylib/__init__.py + grep "GREETING" /tmp/monorepo/unpacked/shared/mylib/__init__.py + +restore: | + cd /tmp/monorepo/charm 2>/dev/null && charmcraft clean || true + rm -rf /tmp/monorepo From ac49e290f13e438de2ffab09fad0a5a90e9b21a5 Mon Sep 17 00:00:00 2001 From: Workshop Date: Wed, 8 Jul 2026 13:27:58 -0400 Subject: [PATCH 4/6] build: pin craft-parts and craft-application to CHARMCRAFT-710 prototype branches Temporarily pin both dependencies to the work/CHARMCRAFT-710-prototype branches while the upstream PRs are in review. CHARMCRAFT-710 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --- pyproject.toml | 7 +++++ uv.lock | 70 +++++++++++++++----------------------------------- 2 files changed, 28 insertions(+), 49 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index a8acd8d55..f7e649e4c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -505,6 +505,13 @@ url = "https://people.canonical.com/~lengau/python-apt-ubuntu-wheels/" explicit = true [tool.uv.sources] +craft-application = { git = "https://github.com/canonical/craft-application.git", branch = "work/CHARMCRAFT-710-prototype" } +craft-cli = { git = "https://github.com/canonical/craft-cli.git", branch = "main" } +craft-grammar = { git = "https://github.com/canonical/craft-grammar.git", branch = "main" } +craft-parts = { git = "https://github.com/canonical/craft-parts.git", branch = "work/CHARMCRAFT-710-prototype" } +craft-providers = { git = "https://github.com/canonical/craft-providers.git", branch = "main" } +craft-platforms = { git = "https://github.com/canonical/craft-platforms.git", branch = "main" } +craft-store = { git = "https://github.com/canonical/craft-store.git", branch = "main" } python-apt = { index = "python-apt-wheels" } [tool.ty.src] diff --git a/uv.lock b/uv.lock index 6d4ffc57d..1c3be28b2 100644 --- a/uv.lock +++ b/uv.lock @@ -526,13 +526,13 @@ types = [ [package.metadata] requires-dist = [ - { name = "craft-application", specifier = "~=7.0" }, - { name = "craft-cli", specifier = "~=3.4" }, - { name = "craft-grammar", specifier = ">=2.0.0" }, - { name = "craft-parts", specifier = "~=2.20" }, - { name = "craft-platforms", specifier = "~=0.10" }, - { name = "craft-providers", specifier = ">=3.4.0,<4.0" }, - { name = "craft-store", specifier = "~=3.2" }, + { name = "craft-application", git = "https://github.com/canonical/craft-application.git?branch=work%2FCHARMCRAFT-710-prototype" }, + { name = "craft-cli", git = "https://github.com/canonical/craft-cli.git?branch=main" }, + { name = "craft-grammar", git = "https://github.com/canonical/craft-grammar.git?branch=main" }, + { name = "craft-parts", git = "https://github.com/canonical/craft-parts.git?branch=work%2FCHARMCRAFT-710-prototype" }, + { name = "craft-platforms", git = "https://github.com/canonical/craft-platforms.git?branch=main" }, + { name = "craft-providers", git = "https://github.com/canonical/craft-providers.git?branch=main" }, + { name = "craft-store", git = "https://github.com/canonical/craft-store.git?branch=main" }, { name = "distro", specifier = ">=1.7.0" }, { name = "docker", specifier = ">=7.0.0" }, { name = "humanize", specifier = ">=2.6.0" }, @@ -907,8 +907,8 @@ toml = [ [[package]] name = "craft-application" -version = "7.0.0" -source = { registry = "https://pypi.org/simple" } +version = "7.0.0.post14+gb0a02d5" +source = { git = "https://github.com/canonical/craft-application.git?branch=work%2FCHARMCRAFT-710-prototype#b0a02d5cbeb58e1740df7872b405b17e55b2463d" } dependencies = [ { name = "annotated-types" }, { name = "craft-archives" }, @@ -930,10 +930,6 @@ dependencies = [ { name = "snap-http" }, { name = "typing-extensions" }, ] -sdist = { url = "https://files.pythonhosted.org/packages/b5/82/f364723d620fd5e96e2d1a2a4e0f975113f3be4650923cd028ae33f1c1a0/craft_application-7.0.0.tar.gz", hash = "sha256:f341e05992b8f64f1d86ec927e3bb66ec72abcecdbca02117a99fd3b4c093715", size = 656712, upload-time = "2026-06-02T21:33:43.975Z" } -wheels = [ - { url = "https://files.pythonhosted.org/packages/00/eb/37b78a3d15028840f94d260e973a7c6163b824b76faeaa95560080c0f850/craft_application-7.0.0-py3-none-any.whl", hash = "sha256:dc521efbf0bed63c0a68f84a79d818d31205a3fcd09090813e4a8c779ca71c3c", size = 206693, upload-time = "2026-06-02T21:33:41.952Z" }, -] [[package]] name = "craft-archives" @@ -955,36 +951,28 @@ wheels = [ [[package]] name = "craft-cli" -version = "3.4.0" -source = { registry = "https://pypi.org/simple" } +version = "999.0.0.dev0" +source = { git = "https://github.com/canonical/craft-cli.git?branch=main#f8b9353f49761d90fcbefde1b8413087be81a5bb" } dependencies = [ { name = "jinja2" }, { name = "platformdirs" }, { name = "pywin32", marker = "sys_platform == 'win32' or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-noble') or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-plucky') or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-questing') or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-resolute') or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-stonking') or (extra == 'group-10-charmcraft-dev-noble' and extra == 'group-10-charmcraft-dev-plucky') or (extra == 'group-10-charmcraft-dev-noble' and extra == 'group-10-charmcraft-dev-questing') or (extra == 'group-10-charmcraft-dev-noble' and extra == 'group-10-charmcraft-dev-resolute') or (extra == 'group-10-charmcraft-dev-noble' and extra == 'group-10-charmcraft-dev-stonking') or (extra == 'group-10-charmcraft-dev-plucky' and extra == 'group-10-charmcraft-dev-questing') or (extra == 'group-10-charmcraft-dev-plucky' and extra == 'group-10-charmcraft-dev-resolute') or (extra == 'group-10-charmcraft-dev-plucky' and extra == 'group-10-charmcraft-dev-stonking') or (extra == 'group-10-charmcraft-dev-questing' and extra == 'group-10-charmcraft-dev-resolute') or (extra == 'group-10-charmcraft-dev-questing' and extra == 'group-10-charmcraft-dev-stonking') or (extra == 'group-10-charmcraft-dev-resolute' and extra == 'group-10-charmcraft-dev-stonking')" }, { name = "typing-extensions" }, ] -sdist = { url = "https://files.pythonhosted.org/packages/21/f8/6e4414523405f439f99ad1fa8b8839bf2a6030e569c1dee89e3e97a8ac15/craft_cli-3.4.0.tar.gz", hash = "sha256:72e7494c66cb78ba08a80b20685dbaa739c7ef18b2fafbde3105958ab55ae7aa", size = 231221, upload-time = "2026-04-07T21:45:10.604Z" } -wheels = [ - { url = "https://files.pythonhosted.org/packages/dc/9f/48733917496a7ddcd503768be1e6dd18e13ed30714a6f63b32ae27d45bf2/craft_cli-3.4.0-py3-none-any.whl", hash = "sha256:ad5bf69e86979a51824bca595a4df5d6e9572346be9ffbdab58b078b9b1cb7cc", size = 47271, upload-time = "2026-04-07T21:45:08.506Z" }, -] [[package]] name = "craft-grammar" -version = "2.3.0" -source = { registry = "https://pypi.org/simple" } +version = "999.0.0.dev0" +source = { git = "https://github.com/canonical/craft-grammar.git?branch=main#4070c51fcb29edbd1fb093bda597ba9909ba7fe7" } dependencies = [ { name = "overrides" }, { name = "pydantic" }, ] -sdist = { url = "https://files.pythonhosted.org/packages/c7/35/584fc928bffd1346c4b9c55170cbe4c09f89ec185d0d9d7e2626f876e80d/craft_grammar-2.3.0.tar.gz", hash = "sha256:0b7ae3aa595f0f3d1f82ed2e696c99b35283c18a60c7a68840bc185bd123e4d8", size = 147552, upload-time = "2025-09-19T15:51:16.29Z" } -wheels = [ - { url = "https://files.pythonhosted.org/packages/6d/ce/0edcd8a0b0ab73f43bb5197e7f61d2be0c0fd129451936659353553f5037/craft_grammar-2.3.0-py3-none-any.whl", hash = "sha256:4a709037a7a2bdbc8362ef97645dfb86d4c67eac31058482704cba074f49507b", size = 27772, upload-time = "2025-09-19T15:51:14.794Z" }, -] [[package]] name = "craft-parts" -version = "2.34.0" -source = { registry = "https://pypi.org/simple" } +version = "2.35.0.post11+g38ddeefa" +source = { git = "https://github.com/canonical/craft-parts.git?branch=work%2FCHARMCRAFT-710-prototype#38ddeefa5aa3b3d2120d2b9ca5e635b019efb802" } dependencies = [ { name = "lxml" }, { name = "pydantic" }, @@ -996,29 +984,21 @@ dependencies = [ { name = "tomli", marker = "python_full_version < '3.11' or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-noble') or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-plucky') or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-questing') or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-resolute') or (extra == 'group-10-charmcraft-dev-jammy' and extra == 'group-10-charmcraft-dev-stonking') or (extra == 'group-10-charmcraft-dev-noble' and extra == 'group-10-charmcraft-dev-plucky') or (extra == 'group-10-charmcraft-dev-noble' and extra == 'group-10-charmcraft-dev-questing') or (extra == 'group-10-charmcraft-dev-noble' and extra == 'group-10-charmcraft-dev-resolute') or (extra == 'group-10-charmcraft-dev-noble' and extra == 'group-10-charmcraft-dev-stonking') or (extra == 'group-10-charmcraft-dev-plucky' and extra == 'group-10-charmcraft-dev-questing') or (extra == 'group-10-charmcraft-dev-plucky' and extra == 'group-10-charmcraft-dev-resolute') or (extra == 'group-10-charmcraft-dev-plucky' and extra == 'group-10-charmcraft-dev-stonking') or (extra == 'group-10-charmcraft-dev-questing' and extra == 'group-10-charmcraft-dev-resolute') or (extra == 'group-10-charmcraft-dev-questing' and extra == 'group-10-charmcraft-dev-stonking') or (extra == 'group-10-charmcraft-dev-resolute' and extra == 'group-10-charmcraft-dev-stonking')" }, { name = "zstandard" }, ] -sdist = { url = "https://files.pythonhosted.org/packages/e1/dc/a024e00afcaac70a1741a342e4de7a9c715b230875779058b84c2f088099/craft_parts-2.34.0.tar.gz", hash = "sha256:644c1733d29fbabff0dbb088a18b877652b4099de07a9f90563ed1fb6e620ce7", size = 1013434, upload-time = "2026-06-11T12:04:01.725Z" } -wheels = [ - { url = "https://files.pythonhosted.org/packages/29/a9/f344547c792d9f8dd93e130ba5be5c5dd7d120f8196393c51fd023f1861a/craft_parts-2.34.0-py3-none-any.whl", hash = "sha256:bfba031d8974c1b43c1266c1eb00f29f9eaef524ea59c95df9a7729b48eb18d1", size = 555932, upload-time = "2026-06-11T12:03:59.481Z" }, -] [[package]] name = "craft-platforms" -version = "0.11.1" -source = { registry = "https://pypi.org/simple" } +version = "999.0.0.dev0" +source = { git = "https://github.com/canonical/craft-platforms.git?branch=main#e8b89ce740e97e4b1bdd3619d5c490766cdf865d" } dependencies = [ { name = "annotated-types" }, { name = "distro" }, { name = "typing-extensions" }, ] -sdist = { url = "https://files.pythonhosted.org/packages/93/b9/b7bef735949e73756910d85c1d4178e5c6523b70e5dbe5477ab0c2fd8d81/craft_platforms-0.11.1.tar.gz", hash = "sha256:5807e2b727c0cb9c7c85e5ecaf4181ed1b3f89e6232464736369dcb871ae9339", size = 355329, upload-time = "2026-04-09T14:07:58.52Z" } -wheels = [ - { url = "https://files.pythonhosted.org/packages/42/77/d2a19bde5e05ec30eef8f63f6f6e1cde9c4f07be5da7fb71a675e159eec2/craft_platforms-0.11.1-py3-none-any.whl", hash = "sha256:740dc7ba7f508a2fe8f3f8f8a6784fd70d48b36a2930a418a19c69cefe68d398", size = 37897, upload-time = "2026-04-09T14:07:56.931Z" }, -] [[package]] name = "craft-providers" -version = "3.6.0" -source = { registry = "https://pypi.org/simple" } +version = "999.0.0.dev0" +source = { git = "https://github.com/canonical/craft-providers.git?branch=main#74d275d830fefa4d100958a912b61ba79a8359f9" } dependencies = [ { name = "packaging" }, { name = "pydantic" }, @@ -1027,15 +1007,11 @@ dependencies = [ { name = "requests" }, { name = "requests-unixsocket2" }, ] -sdist = { url = "https://files.pythonhosted.org/packages/47/bc/db06baf74ff9538282eb265f99b0147f3b8b775da583a9c6aa88a9d59227/craft_providers-3.6.0.tar.gz", hash = "sha256:dfffebb4a9f09f763b293fe396f9f4f17d917e18167d98b61f76cffd55556250", size = 325499, upload-time = "2026-04-30T17:43:56.728Z" } -wheels = [ - { url = "https://files.pythonhosted.org/packages/ce/88/a8cebf86e8fda0c542e70c40374d3edc0bf4cf92ba55151e3a4f60695253/craft_providers-3.6.0-py3-none-any.whl", hash = "sha256:3b3ee87e535f1a29555012ba8d050ae6ca9afbc91fc2f273656d57052a307854", size = 121782, upload-time = "2026-04-30T17:43:54.567Z" }, -] [[package]] name = "craft-store" -version = "3.3.0" -source = { registry = "https://pypi.org/simple" } +version = "999.0.0.dev0" +source = { git = "https://github.com/canonical/craft-store.git?branch=main#19166ba4b222b72e3fd1a9f817f26fcf82d2ec54" } dependencies = [ { name = "annotated-types" }, { name = "httpx" }, @@ -1049,10 +1025,6 @@ dependencies = [ { name = "requests-toolbelt" }, { name = "typing-extensions" }, ] -sdist = { url = "https://files.pythonhosted.org/packages/c4/64/af2af291aef5ea2b5fc56d9be151324eabb55c4ed89bc4f11343faa377b5/craft_store-3.3.0.tar.gz", hash = "sha256:02304296d7d5b896bb8d07660c3a29eaff461fc12d40fd2a21a39230f53c288b", size = 217863, upload-time = "2025-07-02T14:09:49.221Z" } -wheels = [ - { url = "https://files.pythonhosted.org/packages/e0/81/14c738f7d95737a49d753e0b453c09bf8e9e096d54023200d27a6d58398a/craft_store-3.3.0-py3-none-any.whl", hash = "sha256:e1c8597653922f615db7d23cdc9b8774abc6b7cb18217252266ddbaa05a1c330", size = 52612, upload-time = "2025-07-02T14:09:47.962Z" }, -] [[package]] name = "crashtest" From 9fbdd867684b717cdcd124a9f3fdc814ff6d1f8f Mon Sep 17 00:00:00 2001 From: Workshop Date: Fri, 10 Jul 2026 14:21:40 -0400 Subject: [PATCH 5/6] build: pin to work/CHARMCRAFT-710-prototype-e2e branches Update craft-parts and craft-application pins to the e2e branch, which propagates root_dir end-to-end without mutating parts data. CHARMCRAFT-710 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --- pyproject.toml | 4 ++-- uv.lock | 10 +++++----- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index f7e649e4c..f49447061 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -505,10 +505,10 @@ url = "https://people.canonical.com/~lengau/python-apt-ubuntu-wheels/" explicit = true [tool.uv.sources] -craft-application = { git = "https://github.com/canonical/craft-application.git", branch = "work/CHARMCRAFT-710-prototype" } +craft-application = { git = "https://github.com/canonical/craft-application.git", branch = "work/CHARMCRAFT-710-prototype-e2e" } craft-cli = { git = "https://github.com/canonical/craft-cli.git", branch = "main" } craft-grammar = { git = "https://github.com/canonical/craft-grammar.git", branch = "main" } -craft-parts = { git = "https://github.com/canonical/craft-parts.git", branch = "work/CHARMCRAFT-710-prototype" } +craft-parts = { git = "https://github.com/canonical/craft-parts.git", branch = "work/CHARMCRAFT-710-prototype-e2e" } craft-providers = { git = "https://github.com/canonical/craft-providers.git", branch = "main" } craft-platforms = { git = "https://github.com/canonical/craft-platforms.git", branch = "main" } craft-store = { git = "https://github.com/canonical/craft-store.git", branch = "main" } diff --git a/uv.lock b/uv.lock index 1c3be28b2..b53c26b2e 100644 --- a/uv.lock +++ b/uv.lock @@ -526,10 +526,10 @@ types = [ [package.metadata] requires-dist = [ - { name = "craft-application", git = "https://github.com/canonical/craft-application.git?branch=work%2FCHARMCRAFT-710-prototype" }, + { name = "craft-application", git = "https://github.com/canonical/craft-application.git?branch=work%2FCHARMCRAFT-710-prototype-e2e" }, { name = "craft-cli", git = "https://github.com/canonical/craft-cli.git?branch=main" }, { name = "craft-grammar", git = "https://github.com/canonical/craft-grammar.git?branch=main" }, - { name = "craft-parts", git = "https://github.com/canonical/craft-parts.git?branch=work%2FCHARMCRAFT-710-prototype" }, + { name = "craft-parts", git = "https://github.com/canonical/craft-parts.git?branch=work%2FCHARMCRAFT-710-prototype-e2e" }, { name = "craft-platforms", git = "https://github.com/canonical/craft-platforms.git?branch=main" }, { name = "craft-providers", git = "https://github.com/canonical/craft-providers.git?branch=main" }, { name = "craft-store", git = "https://github.com/canonical/craft-store.git?branch=main" }, @@ -908,7 +908,7 @@ toml = [ [[package]] name = "craft-application" version = "7.0.0.post14+gb0a02d5" -source = { git = "https://github.com/canonical/craft-application.git?branch=work%2FCHARMCRAFT-710-prototype#b0a02d5cbeb58e1740df7872b405b17e55b2463d" } +source = { git = "https://github.com/canonical/craft-application.git?branch=work%2FCHARMCRAFT-710-prototype-e2e#b0a02d5cbeb58e1740df7872b405b17e55b2463d" } dependencies = [ { name = "annotated-types" }, { name = "craft-archives" }, @@ -971,8 +971,8 @@ dependencies = [ [[package]] name = "craft-parts" -version = "2.35.0.post11+g38ddeefa" -source = { git = "https://github.com/canonical/craft-parts.git?branch=work%2FCHARMCRAFT-710-prototype#38ddeefa5aa3b3d2120d2b9ca5e635b019efb802" } +version = "2.35.0.post20+g2e9b7fca" +source = { git = "https://github.com/canonical/craft-parts.git?branch=work%2FCHARMCRAFT-710-prototype-e2e#2e9b7fca225f7ddbf80bacd4a30ac806b3614725" } dependencies = [ { name = "lxml" }, { name = "pydantic" }, From c9cb21e2f65e10f37e07600c5619169cb07410d8 Mon Sep 17 00:00:00 2001 From: Workshop Date: Fri, 10 Jul 2026 15:58:21 -0400 Subject: [PATCH 6/6] fix(spread): address Copilot review suggestions on monorepo test - Install python3-yaml explicitly rather than relying on it being present - Use yaml.safe_dump instead of yaml.dump - Add microk8s status --wait-ready before enabling addons Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> --- tests/spread/charms/k8s-operator/task.yaml | 1 + tests/spread/charms/monorepo/task.yaml | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/tests/spread/charms/k8s-operator/task.yaml b/tests/spread/charms/k8s-operator/task.yaml index d404549eb..a65e21ce6 100644 --- a/tests/spread/charms/k8s-operator/task.yaml +++ b/tests/spread/charms/k8s-operator/task.yaml @@ -32,6 +32,7 @@ environment: prepare: | snap install microk8s --channel=1.28-strict/stable + microk8s status --wait-ready microk8s enable hostpath-storage microk8s enable dns snap alias microk8s.kubectl kubectl diff --git a/tests/spread/charms/monorepo/task.yaml b/tests/spread/charms/monorepo/task.yaml index 870e243f8..cf6644a59 100644 --- a/tests/spread/charms/monorepo/task.yaml +++ b/tests/spread/charms/monorepo/task.yaml @@ -17,6 +17,7 @@ environment: CHARM_SUBDIR/mysql_router_operators_kubernetes: kubernetes prepare: | + apt-get install -y python3-yaml git clone --depth=1 https://github.com/canonical/"${REPO}".git /tmp/"${REPO}" python3 - << 'EOF' import os, yaml, pathlib @@ -24,7 +25,7 @@ prepare: | d = yaml.safe_load(p.read_text()) d["parts"].pop("files", None) d["parts"].get("charm-poetry", {}).pop("override-build", None) - p.write_text(yaml.dump(d)) + p.write_text(yaml.safe_dump(d)) EOF restore: |