def _obtain(self, allow_all: bool = False, unpack: bool = True) -> None:
        """Fetch the link of the candidate and unpack to local if necessary.

        :param allow_all: If true, don't validate the wheel tag nor hashes
        :param unpack: Whether to download and unpack the link if it's not local
        """
        if self._cached and self._wheel_compatible(self._cached.name, allow_all):
            return

        if self._source_dir and self._source_dir.exists():
            return

        sources = filtered_sources(self.environment.project.sources, self.req.key)
        env_spec = self.environment.allow_all_spec if allow_all else self.environment.spec
        with self.environment.get_finder(sources, env_spec=env_spec) as finder:
            if not self.link or (self.link.is_wheel and not self._wheel_compatible(self.link.filename, allow_all)):
                if self.req.is_file_or_url:
                    raise CandidateNotFound(f"The URL requirement {self.req.as_line()} is a wheel but incompatible")
                self.link = self._cached = None  # reset the incompatible wheel
                self.link = _find_best_match_link(
                    finder, self.req.as_pinned_version(self.candidate.version), self.candidate.hashes
                )
                if not self.link:
                    raise CandidateNotFound(
                        f"No candidate is found for `{self.req.project_name}` that matches the environment or hashes"
                    )
                if not self.candidate.link:
                    self.candidate.link = self.link
        # find if there is any build cache for the candidate
        if not self.req.editable:
            cached = self._get_build_cache()
            if cached and self._wheel_compatible(cached.name, allow_all):
                self._cached = cached
                return
        # If not, download and unpack the link
        if unpack:
            self._unpack(validate_hashes=not allow_all)
Fetch the link of the candidate and unpack to local if necessary.

        :param allow_all: If true, don't validate the wheel tag nor hashes
        :param unpack: Whether to download and unpack the link if it's not local
        
src/pdm/models/candidates.py