Skip to content

fasta_lake.canonical#

fasta_lake.canonical #

Canonical database management for FastaLake baseline comparisons.

Downloads and manages canonical SwissProt FASTAs for the baseline search that FastaLake is benchmarked against.

download_canonical #

download_canonical(organism: str = 'human', output_dir: str | Path = '.', force: bool = False) -> Path

Download the latest canonical SwissProt FASTA for an organism.

Parameters:

Name Type Description Default
organism str

'human', 'mouse', or 'rat'.

'human'
output_dir path

Where to save the FASTA.

'.'
force bool

Re-download even if file exists.

False

Returns:

Type Description
Path

Path to the downloaded FASTA.

Source code in fasta_lake/canonical.py
def download_canonical(
    organism: str = "human",
    output_dir: str | Path = ".",
    force: bool = False,
) -> Path:
    """Download the latest canonical SwissProt FASTA for an organism.

    Parameters
    ----------
    organism : str
        'human', 'mouse', or 'rat'.
    output_dir : path
        Where to save the FASTA.
    force : bool
        Re-download even if file exists.

    Returns
    -------
    Path
        Path to the downloaded FASTA.
    """
    if organism not in UNIPROT_URLS:
        raise ValueError(f"Unknown organism: {organism}. Available: {list(UNIPROT_URLS)}")

    output_dir = Path(output_dir)
    output_dir.mkdir(parents=True, exist_ok=True)
    output_path = output_dir / f"swissprot_{organism}_canonical.fasta"

    if output_path.exists() and not force:
        n = count_fasta_headers(output_path)
        logger.info("Canonical already exists: %s (%d entries)", output_path, n)
        return output_path

    url = UNIPROT_URLS[organism]
    logger.info("Downloading canonical %s from UniProt...", organism)

    try:
        req = urllib.request.Request(url)
        req.add_header("User-Agent", _user_agent())

        with urllib.request.urlopen(req) as response:
            content = response.read()

        output_path.write_bytes(content)
        n = count_fasta_headers(output_path)
        logger.info("Downloaded: %s (%d entries)", output_path.name, n)

    except Exception as e:
        logger.error("Download failed: %s", e)
        # Fall back to local copy if available
        local = _find_local_canonical(organism)
        if local:
            logger.info("Using local copy: %s", local)
            shutil.copy2(local, output_path)
        else:
            raise

    return output_path

get_canonical #

get_canonical(organism: str = 'human') -> Path | None

Get path to canonical FASTA, preferring local copy.

Does NOT download — returns None if not found locally. Use download_canonical() to fetch from UniProt.

Source code in fasta_lake/canonical.py
def get_canonical(organism: str = "human") -> Path | None:
    """Get path to canonical FASTA, preferring local copy.

    Does NOT download — returns None if not found locally.
    Use download_canonical() to fetch from UniProt.
    """
    local = _find_local_canonical(organism)
    if local:
        return local

    # Check common cluster paths
    import os

    peter = os.environ.get("PETER")
    if not peter:
        return None
    cluster_paths = [
        Path(peter) / "FastaLake" / "databases" / "isoforms" / organism / "uniprot",
    ]

    for p in cluster_paths:
        if not p.exists():
            continue
        for f in sorted(p.glob("swissprot_*reviewed*.fasta"), reverse=True):
            return f

    return None