Files
geMoldInsight/venv/lib/python3.11/site-packages/scooby/knowledge.py
T

228 lines
5.5 KiB
Python
Raw Normal View History

2026-02-12 23:22:11 +08:00
"""The knowledge base.
Knowledge
=========
It contains, for instance, known odd locations of version information for
particular modules (``VERSION_ATTRIBUTES``, ``VERSION_METHODS``)
"""
from __future__ import annotations
from pathlib import Path
import sys
import sysconfig
from typing import TYPE_CHECKING, Literal
if TYPE_CHECKING:
from collections.abc import Callable
PACKAGE_ALIASES = {
'vtkmodules': 'vtk',
'vtkmodules.all': 'vtk',
}
# Define unusual version locations
VERSION_ATTRIBUTES = {
'PyQt5': 'Qt.PYQT_VERSION_STR',
'sip': 'SIP_VERSION_STR',
}
def get_pyqt5_version() -> str:
"""Return the PyQt5 version."""
try:
from PyQt5.Qt import PYQT_VERSION_STR
except ImportError:
return 'Version unknown'
return PYQT_VERSION_STR
VERSION_METHODS: dict[str, Callable[[], str]] = {
'PyQt5': get_pyqt5_version,
}
# Check the environments
def in_ipython() -> bool:
"""Check if we are in a IPython environment.
Returns
-------
bool : True
``True`` when in an IPython environment.
"""
try:
__IPYTHON__ # noqa: B018
except NameError:
return False
else:
return True
def in_ipykernel() -> bool:
"""Check if in a ipykernel (most likely Jupyter) environment.
Warning:
-------
There is no way to tell if the code is being executed in a notebook
(Jupyter Notebook or Jupyter Lab) or a kernel is used but executed in a
QtConsole, or in an IPython console, or any other frontend GUI. However, if
`in_ipykernel` returns True, you are most likely in a Jupyter Notebook/Lab,
just keep it in mind that there are other possibilities.
Returns:
-------
bool : True if using an ipykernel
"""
ipykernel = False
if in_ipython():
try:
ipykernel: bool = type(get_ipython()).__module__.startswith('ipykernel.')
except NameError:
pass
return ipykernel
def get_standard_lib_modules() -> set[str]:
"""Return a set of the names of all modules in the standard library."""
site_path = Path(sysconfig.get_path('stdlib'))
if getattr(sys, 'frozen', False): # within pyinstaller
lib_path = site_path / '..'
if lib_path.is_dir():
names = lib_path.iterdir()
stdlib_pkgs = {p.stem for p in names if p.suffix == '.py'}
else:
stdlib_pkgs = {}
else:
names = site_path.iterdir()
stdlib_pkgs = {p.stem if p.suffix == '.py' else p.name for p in names}
return {
'python',
'sys',
'__builtin__',
'__builtins__',
'builtins',
'session',
'math',
'itertools',
'binascii',
'array',
'atexit',
'fcntl',
'errno',
'gc',
'time',
'unicodedata',
'mmap',
}.union(stdlib_pkgs)
def version_tuple(v: str) -> tuple[int, ...]:
"""Convert a version string to a tuple containing ints.
Non-numeric version strings will be converted to 0. For example:
``'0.28.0dev0'`` will be converted to ``'0.28.0'``
Returns
-------
ver_tuple : tuple
Length 3 tuple representing the major, minor, and patch
version.
"""
split_v = v.split('.')
while len(split_v) < 3:
split_v.append('0')
if len(split_v) > 3:
msg = 'Version strings containing more than three parts cannot be parsed'
raise ValueError(msg)
vals: list[int] = []
for item in split_v:
if item.isnumeric():
vals.append(int(item))
else:
vals.append(0)
return tuple(vals)
def meets_version(version: str, meets: str) -> bool:
"""Check if a version string meets a minimum version.
This is a simplified way to compare version strings. For a more robust
tool, please check out the ``packaging`` library:
https://github.com/pypa/packaging
Parameters
----------
version : str
Version string. For example ``'0.25.1'``.
meets : str
Version string. For example ``'0.25.2'``.
Returns
-------
newer : bool
True if version ``version`` is greater or equal to version ``meets``.
Examples
--------
>>> meets_version('0.25.1', '0.25.2')
False
>>> meets_version('0.26.0', '0.25.2')
True
"""
va = version_tuple(version)
vb = version_tuple(meets)
if len(va) != len(vb):
msg = 'Versions are not comparable.'
raise AssertionError(msg)
for i in range(len(va)):
if va[i] > vb[i]:
return True
if va[i] < vb[i]:
return False
# Arrived here if same version
return True
def get_filesystem_type() -> str | Literal[False]:
"""Get the type of the file system at the path of the scooby package."""
try:
import psutil # lazy-load see PR#85
except ImportError:
psutil = False
from pathlib import Path # lazy-load see PR#85
import platform # lazy-load see PR#85
# Skip Windows due to https://github.com/banesullivan/scooby/issues/75
fs_type: str | Literal[False]
if psutil and platform.system() != 'Windows':
# Code by https://stackoverflow.com/a/35291824/10504481
my_path = str(Path(__file__).resolve())
best_match = ''
fs_type = ''
for part in psutil.disk_partitions():
if my_path.startswith(part.mountpoint) and len(best_match) < len(part.mountpoint):
fs_type = part.fstype
best_match = part.mountpoint
else:
fs_type = False
return fs_type