Skip to content

Commit

Permalink
fix(expand-extensions): use the Application's project
Browse files Browse the repository at this point in the history
Fixes LP bug https://bugs.launchpad.net/snapcraft/+bug/2083964

Instead of parsing the project again itself, expand-extensions now uses
the project provided by the application. The output is changed slightly,
but I believe it reflects a more accurate expansion.
  • Loading branch information
lengau committed Oct 9, 2024
1 parent 82fa41a commit b165507
Show file tree
Hide file tree
Showing 3 changed files with 53 additions and 35 deletions.
26 changes: 6 additions & 20 deletions snapcraft/commands/extensions.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

"""Snapcraft extension commands."""

import argparse
import textwrap
from typing import Dict, List

Expand Down Expand Up @@ -114,25 +115,10 @@ class ExpandExtensionsCommand(AppCommand):
"""
)

always_load_project = True

@overrides
def run(self, parsed_args):
snap_project = get_snap_project()

# load yaml file and trigger legacy behavior if base is core, core18, or core20
yaml_data = process_yaml(snap_project.project_file)

# process yaml before unmarshalling the data
arch = get_host_architecture()
yaml_data_for_arch = apply_yaml(yaml_data, arch, arch)

# `apply_yaml()` adds or replaces the architectures keyword with an Architecture
# object, which does not easily dump to a yaml file
yaml_data_for_arch.pop("architectures", None)
yaml_data_for_arch.pop("platforms", None)

# `parse-info` keywords must be removed before unmarshalling, because they are
# not part of the Project model
extract_parse_info(yaml_data_for_arch)

project_data = models.Project.unmarshal(yaml_data_for_arch)
emit.message(project_data.to_yaml_string())
emit.message(
self._services.project.to_yaml_string()
)
56 changes: 41 additions & 15 deletions tests/unit/commands/test_expand_extensions.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@
import pytest
from craft_platforms import DebianArchitecture

from snapcraft import commands, const
from snapcraft import application, commands, const


@dataclass
Expand All @@ -45,7 +45,7 @@ def valid_core_data(request) -> CoreData:


@pytest.mark.usefixtures("fake_extension")
def test_expand_extensions_simple_core22(new_dir, emitter):
def test_expand_extensions_simple_core22(new_dir, emitter, mocker):
"""Expand an extension for a simple snapcraft.yaml file."""
with Path("snapcraft.yaml").open("w") as yaml_file:
print(
Expand Down Expand Up @@ -73,8 +73,8 @@ def test_expand_extensions_simple_core22(new_dir, emitter):
file=yaml_file,
)

cmd = commands.ExpandExtensionsCommand(None)
cmd.run(Namespace())
mocker.patch("sys.argv", ["snapcraft", "expand-extensions"])
application.main()
emitter.assert_message(
dedent(
f"""\
Expand Down Expand Up @@ -110,7 +110,7 @@ def test_expand_extensions_simple_core22(new_dir, emitter):


@pytest.mark.usefixtures("fake_extension")
def test_expand_extensions_simple(new_dir, emitter, valid_core_data):
def test_expand_extensions_simple(new_dir, emitter, valid_core_data, mocker):
"""Expand an extension for a simple snapcraft.yaml file."""
with Path("snapcraft.yaml").open("w") as yaml_file:
print(
Expand Down Expand Up @@ -139,8 +139,8 @@ def test_expand_extensions_simple(new_dir, emitter, valid_core_data):
file=yaml_file,
)

cmd = commands.ExpandExtensionsCommand(None)
cmd.run(Namespace())
mocker.patch("sys.argv", ["snapcraft", "expand-extensions"])
application.main()
emitter.assert_message(
dedent(
f"""\
Expand Down Expand Up @@ -216,8 +216,8 @@ def test_expand_extensions_complex_core22(new_dir, emitter, mocker):
file=yaml_file,
)

cmd = commands.ExpandExtensionsCommand(None)
cmd.run(Namespace())
mocker.patch("sys.argv", ["snapcraft", "expand-extensions"])
application.main()
emitter.assert_message(
dedent(
f"""\
Expand All @@ -241,9 +241,17 @@ def test_expand_extensions_complex_core22(new_dir, emitter, mocker):
grade: stable
architectures:
- build-on:
- {DebianArchitecture.from_host()}
- amd64
build-for:
- {DebianArchitecture.from_host()}
- amd64
- build-on:
- arm64
build-for:
- arm64
- build-on:
- armhf
build-for:
- armhf
apps:
app1:
command: app1
Expand Down Expand Up @@ -279,7 +287,10 @@ def test_expand_extensions_complex(new_dir, emitter, mocker, valid_core_data):
build-base: {valid_core_data.build_base}
confinement: strict
grade: {valid_core_data.grade}
platforms: [amd64, arm64, armhf]
platforms:
amd64:
arm64:
armhf:
apps:
app1:
Expand All @@ -301,9 +312,8 @@ def test_expand_extensions_complex(new_dir, emitter, mocker, valid_core_data):
),
file=yaml_file,
)

cmd = commands.ExpandExtensionsCommand(None)
cmd.run(Namespace())
mocker.patch("sys.argv", ["snapcraft", "expand-extensions"])
application.main()
emitter.assert_message(
dedent(
f"""\
Expand All @@ -313,6 +323,22 @@ def test_expand_extensions_complex(new_dir, emitter, mocker, valid_core_data):
description: expand a fake extension
base: {valid_core_data.base}
build-base: {valid_core_data.build_base}
platforms:
amd64:
build-on:
- amd64
build-for:
- amd64
arm64:
build-on:
- arm64
build-for:
- arm64
armhf:
build-on:
- armhf
build-for:
- armhf
parts:
nil:
plugin: nil
Expand Down
6 changes: 6 additions & 0 deletions tests/unit/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,12 @@ def reset_plugins():
plugins.unregister_all()


@pytest.fixture(autouse=True)
def set_debug(monkeypatch):
# Instead of eating exceptions, calls to app.run() will raise them.
monkeypatch.setenv("CRAFT_DEBUG", "1")


@pytest.fixture
def snapcraft_yaml(new_dir):
"""Return a fixture that can write a snapcraft.yaml."""
Expand Down

0 comments on commit b165507

Please sign in to comment.