def _is_compatible_version(self, built_by: str) -> bool: """Return True if running version is >= built-by version.""" # We use a bit a of naive string check here. Re-using Python # versioning comparisons cannot be used because we don't follow # their spec. Apt version comparison would require running on Linux. return snapcraft._get_version() >= built_by
def annotate_snapcraft(data, parts_dir: str): manifest = OrderedDict() # type: Dict[str, Any] manifest["snapcraft-version"] = snapcraft._get_version() release = os_release.OsRelease() with contextlib.suppress(errors.OsReleaseIdError): manifest["snapcraft-os-release-id"] = release.id() with contextlib.suppress(errors.OsReleaseVersionIdError): manifest["snapcraft-os-release-version-id"] = release.version_id() for k, v in data.items(): manifest[k] = v image_info = os.environ.get("SNAPCRAFT_IMAGE_INFO") if image_info: try: image_info_dict = json.loads(image_info) except json.decoder.JSONDecodeError as exception: raise errors.InvalidContainerImageInfoError( image_info) from exception manifest["image-info"] = image_info_dict for field in ("build-packages", "build-snaps"): manifest[field] = get_global_state().assets.get(field, []) for part in data["parts"]: state_dir = os.path.join(parts_dir, part, "state") pull_state = get_state(state_dir, steps.PULL) manifest["parts"][part]["build-packages"] = pull_state.assets.get( "build-packages", []) manifest["parts"][part]["stage-packages"] = pull_state.assets.get( "stage-packages", []) source_details = pull_state.assets.get("source-details", {}) if source_details: manifest["parts"][part].update(source_details) build_state = get_state(state_dir, steps.BUILD) manifest["parts"][part].update(build_state.assets) return manifest
def _check_environment_needs_cleaning(self) -> bool: info = self._load_info() provider_base = info.get("base") built_by = info.get("created-by-snapcraft-version") build_base = self.project._get_build_base() if provider_base is None or built_by is None: self.echoer.warning( "Build environment is in unknown state, cleaning first." ) return True elif build_base != provider_base: self.echoer.warning( f"Project base changed from {provider_base!r} to {build_base!r}, cleaning first." ) return True elif pkg_resources.parse_version( snapcraft._get_version() ) < pkg_resources.parse_version(built_by): self.echoer.warning( f"Build environment was created with newer snapcraft version {built_by!r}, cleaning first." ) return True return False
def annotate_snapcraft(project: "Project", data: Dict[str, Any]) -> Dict[str, Any]: manifest = OrderedDict() # type: Dict[str, Any] manifest["snapcraft-version"] = snapcraft._get_version() manifest["snapcraft-started-at"] = project._get_start_time().isoformat( ) + "Z" release = os_release.OsRelease() with contextlib.suppress(errors.OsReleaseIdError): manifest["snapcraft-os-release-id"] = release.id() with contextlib.suppress(errors.OsReleaseVersionIdError): manifest["snapcraft-os-release-version-id"] = release.version_id() for k, v in data.items(): manifest[k] = v image_info = os.environ.get("SNAPCRAFT_IMAGE_INFO") if image_info: try: image_info_dict = json.loads(image_info) except json.decoder.JSONDecodeError as exception: raise errors.InvalidContainerImageInfoError( image_info) from exception manifest["image-info"] = image_info_dict global_state = GlobalState.load( filepath=project._get_global_state_file_path()) manifest["build-packages"] = sorted(global_state.get_build_packages()) manifest["build-snaps"] = sorted(global_state.get_build_snaps()) for part in data["parts"]: state_dir = os.path.join(project.parts_dir, part, "state") pull_state = get_state(state_dir, steps.PULL) manifest["parts"][part]["build-packages"] = sorted( pull_state.assets.get("build-packages", [])) manifest["parts"][part]["stage-packages"] = sorted( pull_state.assets.get("stage-packages", [])) source_details = pull_state.assets.get("source-details", {}) if source_details: manifest["parts"][part].update(source_details) build_state = get_state(state_dir, steps.BUILD) manifest["parts"][part].update(build_state.assets) # Assemble all primed stage packages into a single list... primed_stage_packages: Set[str] = set() for part in data["parts"]: state_dir = os.path.join(project.parts_dir, part, "state") prime_state = get_state(state_dir, steps.PRIME) primed_stage_packages |= prime_state.primed_stage_packages manifest["primed-stage-packages"] = sorted(primed_stage_packages) return manifest
def _setup_snapcraft(self) -> None: self._save_info( data={ "base": self.project._get_build_base(), "created-by-snapcraft-version": snapcraft._get_version(), } ) registry_filepath = os.path.join( self.provider_project_dir, "snap-registry.yaml" ) # We do not want to inject from the host if not running from the snap # or if the provider cannot handle snap mounts. # This latter problem should go away when API for retrieving snaps # through snapd is generally available. if self._get_is_snap_injection_capable(): inject_from_host = common.is_snap() else: inject_from_host = False snap_injector = SnapInjector( registry_filepath=registry_filepath, snap_arch=self.project.deb_arch, runner=self._run, file_pusher=self._push_file, inject_from_host=inject_from_host, ) # Note that snap injection order is important. # If the build base is core, we do not need to inject snapd. # Check for None as this build can be driven from a non snappy enabled # system, so we may find ourselves in a situation where the base is not # set like on OSX or Windows. build_base = self.project._get_build_base() if build_base is not None and build_base != "core": snap_injector.add(snap_name="snapd") # Prevent injecting core18 twice. if build_base is not None and build_base != "core18": snap_injector.add(snap_name=build_base) # Inject snapcraft snap_injector.add(snap_name="core18") snap_injector.add(snap_name="snapcraft") snap_injector.apply()
def _setup_snapcraft(self) -> None: self._save_info( data={ "base": self.project._get_build_base(), "created-by-snapcraft-version": snapcraft._get_version(), "host-project-directory": self.project._project_dir, } ) registry_filepath = os.path.join( self.provider_project_dir, "snap-registry.yaml" ) # We do not want to inject from the host if not running from the snap # or if the provider cannot handle snap mounts. # This latter problem should go away when API for retrieving snaps # through snapd is generally available. if self._get_is_snap_injection_capable(): inject_from_host = common.is_snap() else: inject_from_host = False snap_injector = SnapInjector( registry_filepath=registry_filepath, runner=self._run, file_pusher=self._push_file, inject_from_host=inject_from_host, ) snap_injector.add(snap_name="snapd") # Prevent injecting core20 twice (Snapcraft's base). build_base = self.project._get_build_base() if build_base != "core20": snap_injector.add(snap_name=build_base) # Inject snapcraft and its base. snap_injector.add(snap_name="core20") snap_injector.add(snap_name="snapcraft") snap_injector.apply()
def annotate_snapcraft(data, parts_dir: str, global_state_path: str): manifest = OrderedDict() # type: Dict[str, Any] manifest["snapcraft-version"] = snapcraft._get_version() release = os_release.OsRelease() with contextlib.suppress(errors.OsReleaseIdError): manifest["snapcraft-os-release-id"] = release.id() with contextlib.suppress(errors.OsReleaseVersionIdError): manifest["snapcraft-os-release-version-id"] = release.version_id() for k, v in data.items(): manifest[k] = v image_info = os.environ.get("SNAPCRAFT_IMAGE_INFO") if image_info: try: image_info_dict = json.loads(image_info) except json.decoder.JSONDecodeError as exception: raise errors.InvalidContainerImageInfoError(image_info) from exception manifest["image-info"] = image_info_dict global_state = GlobalState.load(filepath=global_state_path) manifest["build-packages"] = global_state.get_build_packages() manifest["build-snaps"] = global_state.get_build_snaps() for part in data["parts"]: state_dir = os.path.join(parts_dir, part, "state") pull_state = get_state(state_dir, steps.PULL) manifest["parts"][part]["build-packages"] = pull_state.assets.get( "build-packages", [] ) manifest["parts"][part]["stage-packages"] = pull_state.assets.get( "stage-packages", [] ) source_details = pull_state.assets.get("source-details", {}) if source_details: manifest["parts"][part].update(source_details) build_state = get_state(state_dir, steps.BUILD) manifest["parts"][part].update(build_state.assets) return manifest
def test_version_from_snap(self): self.useFixture(fixtures.EnvironmentVariable("SNAP_NAME", "snapcraft")) self.useFixture(fixtures.EnvironmentVariable("SNAP_VERSION", "3.14")) self.assertThat(snapcraft._get_version(), Equals("3.14"))
def test_version_from_snap(self): self.useFixture(fixtures.EnvironmentVariable('SNAP_NAME', 'snapcraft')) self.useFixture(fixtures.EnvironmentVariable('SNAP_VERSION', '3.14')) self.assertThat(snapcraft._get_version(), Equals('3.14'))
def test_version_from_snap(self): self.useFixture(fixtures.EnvironmentVariable( 'SNAP_NAME', 'snapcraft')) self.useFixture(fixtures.EnvironmentVariable( 'SNAP_VERSION', '3.14')) self.assertThat(snapcraft._get_version(), Equals('3.14'))