Voice et bot modif

This commit is contained in:
pi 2026-06-16 17:09:34 +00:00
parent 189d56026b
commit 7333a22bcd
10774 changed files with 634644 additions and 933308 deletions

View file

@ -5,8 +5,6 @@ operate. This is expected to be importable from any/all files within the
subpackage and, thus, should not depend on them.
"""
from __future__ import annotations
import configparser
import contextlib
import locale
@ -14,23 +12,19 @@ import logging
import pathlib
import re
import sys
from collections.abc import Iterator
from itertools import chain, groupby, repeat
from typing import TYPE_CHECKING, Literal
from typing import TYPE_CHECKING, Dict, Iterator, List, Optional, Union
from pip._vendor.packaging.requirements import InvalidRequirement
from pip._vendor.packaging.version import InvalidVersion
from pip._vendor.requests.models import Request, Response
from pip._vendor.rich.console import Console, ConsoleOptions, RenderResult
from pip._vendor.rich.markup import escape
from pip._vendor.rich.text import Text
if TYPE_CHECKING:
from hashlib import _Hash
from pip._vendor.requests.models import Request, Response
from typing import Literal
from pip._internal.metadata import BaseDistribution
from pip._internal.network.download import _FileDownload
from pip._internal.req.req_install import InstallRequirement
logger = logging.getLogger(__name__)
@ -44,7 +38,7 @@ def _is_kebab_case(s: str) -> bool:
def _prefix_with_indent(
s: Text | str,
s: Union[Text, str],
console: Console,
*,
prefix: str,
@ -80,13 +74,13 @@ class DiagnosticPipError(PipError):
def __init__(
self,
*,
kind: Literal["error", "warning"] = "error",
reference: str | None = None,
message: str | Text,
context: str | Text | None,
hint_stmt: str | Text | None,
note_stmt: str | Text | None = None,
link: str | None = None,
kind: 'Literal["error", "warning"]' = "error",
reference: Optional[str] = None,
message: Union[str, Text],
context: Optional[Union[str, Text]],
hint_stmt: Optional[Union[str, Text]],
note_stmt: Optional[Union[str, Text]] = None,
link: Optional[str] = None,
) -> None:
# Ensure a proper reference is provided.
if reference is None:
@ -190,21 +184,8 @@ class InstallationError(PipError):
"""General exception during installation"""
class FailedToPrepareCandidate(InstallationError):
"""Raised when we fail to prepare a candidate (i.e. fetch and generate metadata).
This is intentionally not a diagnostic error, since the output will be presented
above this error, when this occurs. This should instead present information to the
user.
"""
def __init__(
self, *, package_name: str, requirement_chain: str, failed_step: str
) -> None:
super().__init__(f"Failed to build '{package_name}' when {failed_step.lower()}")
self.package_name = package_name
self.requirement_chain = requirement_chain
self.failed_step = failed_step
class UninstallationError(PipError):
"""General exception during uninstallation"""
class MissingPyProjectBuildRequires(DiagnosticPipError):
@ -252,7 +233,7 @@ class NoneMetadataError(PipError):
def __init__(
self,
dist: BaseDistribution,
dist: "BaseDistribution",
metadata_name: str,
) -> None:
"""
@ -313,8 +294,8 @@ class NetworkConnectionError(PipError):
def __init__(
self,
error_msg: str,
response: Response | None = None,
request: Request | None = None,
response: Optional[Response] = None,
request: Optional[Request] = None,
) -> None:
"""
Initialize NetworkConnectionError with `request` and `response`
@ -363,7 +344,7 @@ class MetadataInconsistent(InstallationError):
"""
def __init__(
self, ireq: InstallRequirement, field: str, f_val: str, m_val: str
self, ireq: "InstallRequirement", field: str, f_val: str, m_val: str
) -> None:
self.ireq = ireq
self.field = field
@ -377,17 +358,6 @@ class MetadataInconsistent(InstallationError):
)
class MetadataInvalid(InstallationError):
"""Metadata is invalid."""
def __init__(self, ireq: InstallRequirement, error: str) -> None:
self.ireq = ireq
self.error = error
def __str__(self) -> str:
return f"Requested {self.ireq} has invalid metadata: {self.error}"
class InstallationSubprocessError(DiagnosticPipError, InstallationError):
"""A subprocess call failed."""
@ -398,10 +368,10 @@ class InstallationSubprocessError(DiagnosticPipError, InstallationError):
*,
command_description: str,
exit_code: int,
output_lines: list[str] | None,
output_lines: Optional[List[str]],
) -> None:
if output_lines is None:
output_prompt = Text("No available output.")
output_prompt = Text("See above for output.")
else:
output_prompt = (
Text.from_markup(f"[red][{len(output_lines)} lines of output][/]\n")
@ -429,7 +399,7 @@ class InstallationSubprocessError(DiagnosticPipError, InstallationError):
return f"{self.command_description} exited with {self.exit_code}"
class MetadataGenerationFailed(DiagnosticPipError, InstallationError):
class MetadataGenerationFailed(InstallationSubprocessError, InstallationError):
reference = "metadata-generation-failed"
def __init__(
@ -437,7 +407,7 @@ class MetadataGenerationFailed(DiagnosticPipError, InstallationError):
*,
package_details: str,
) -> None:
super().__init__(
super(InstallationSubprocessError, self).__init__(
message="Encountered error while generating package metadata.",
context=escape(package_details),
hint_stmt="See above for details.",
@ -452,9 +422,9 @@ class HashErrors(InstallationError):
"""Multiple HashError instances rolled into one for reporting"""
def __init__(self) -> None:
self.errors: list[HashError] = []
self.errors: List["HashError"] = []
def append(self, error: HashError) -> None:
def append(self, error: "HashError") -> None:
self.errors.append(error)
def __str__(self) -> str:
@ -488,7 +458,7 @@ class HashError(InstallationError):
"""
req: InstallRequirement | None = None
req: Optional["InstallRequirement"] = None
head = ""
order: int = -1
@ -610,7 +580,7 @@ class HashMismatch(HashError):
"someone may have tampered with them."
)
def __init__(self, allowed: dict[str, list[str]], gots: dict[str, _Hash]) -> None:
def __init__(self, allowed: Dict[str, List[str]], gots: Dict[str, "_Hash"]) -> None:
"""
:param allowed: A dict of algorithm names pointing to lists of allowed
hex digests
@ -635,12 +605,12 @@ class HashMismatch(HashError):
"""
def hash_then_or(hash_name: str) -> chain[str]:
def hash_then_or(hash_name: str) -> "chain[str]":
# For now, all the decent hashes have 6-char names, so we can get
# away with hard-coding space literals.
return chain([hash_name], repeat(" or"))
lines: list[str] = []
lines: List[str] = []
for hash_name, expecteds in self.allowed.items():
prefix = hash_then_or(hash_name)
lines.extend((f" Expected {next(prefix)} {e}") for e in expecteds)
@ -661,8 +631,8 @@ class ConfigurationFileCouldNotBeLoaded(ConfigurationError):
def __init__(
self,
reason: str = "could not be loaded",
fname: str | None = None,
error: configparser.Error | None = None,
fname: Optional[str] = None,
error: Optional[configparser.Error] = None,
) -> None:
super().__init__(error)
self.reason = reason
@ -697,7 +667,7 @@ class ExternallyManagedEnvironment(DiagnosticPipError):
reference = "externally-managed-environment"
def __init__(self, error: str | None) -> None:
def __init__(self, error: Optional[str]) -> None:
if error is None:
context = Text(_DEFAULT_EXTERNALLY_MANAGED_ERROR)
else:
@ -724,7 +694,7 @@ class ExternallyManagedEnvironment(DiagnosticPipError):
try:
category = locale.LC_MESSAGES
except AttributeError:
lang: str | None = None
lang: Optional[str] = None
else:
lang, _ = locale.getlocale(category)
if lang is not None:
@ -739,8 +709,8 @@ class ExternallyManagedEnvironment(DiagnosticPipError):
@classmethod
def from_config(
cls,
config: pathlib.Path | str,
) -> ExternallyManagedEnvironment:
config: Union[pathlib.Path, str],
) -> "ExternallyManagedEnvironment":
parser = configparser.ConfigParser(interpolation=None)
try:
parser.read(config, encoding="utf-8")
@ -756,143 +726,3 @@ class ExternallyManagedEnvironment(DiagnosticPipError):
exc_info = logger.isEnabledFor(VERBOSE)
logger.warning("Failed to read %s", config, exc_info=exc_info)
return cls(None)
class UninstallMissingRecord(DiagnosticPipError):
reference = "uninstall-no-record-file"
def __init__(self, *, distribution: BaseDistribution) -> None:
installer = distribution.installer
if not installer or installer == "pip":
dep = f"{distribution.raw_name}=={distribution.version}"
hint = Text.assemble(
"You might be able to recover from this via: ",
(f"pip install --force-reinstall --no-deps {dep}", "green"),
)
else:
hint = Text(
f"The package was installed by {installer}. "
"You should check if it can uninstall the package."
)
super().__init__(
message=Text(f"Cannot uninstall {distribution}"),
context=(
"The package's contents are unknown: "
f"no RECORD file was found for {distribution.raw_name}."
),
hint_stmt=hint,
)
class LegacyDistutilsInstall(DiagnosticPipError):
reference = "uninstall-distutils-installed-package"
def __init__(self, *, distribution: BaseDistribution) -> None:
super().__init__(
message=Text(f"Cannot uninstall {distribution}"),
context=(
"It is a distutils installed project and thus we cannot accurately "
"determine which files belong to it which would lead to only a partial "
"uninstall."
),
hint_stmt=None,
)
class InvalidInstalledPackage(DiagnosticPipError):
reference = "invalid-installed-package"
def __init__(
self,
*,
dist: BaseDistribution,
invalid_exc: InvalidRequirement | InvalidVersion,
) -> None:
installed_location = dist.installed_location
if isinstance(invalid_exc, InvalidRequirement):
invalid_type = "requirement"
else:
invalid_type = "version"
super().__init__(
message=Text(
f"Cannot process installed package {dist} "
+ (f"in {installed_location!r} " if installed_location else "")
+ f"because it has an invalid {invalid_type}:\n{invalid_exc.args[0]}"
),
context=(
"Starting with pip 24.1, packages with invalid "
f"{invalid_type}s can not be processed."
),
hint_stmt="To proceed this package must be uninstalled.",
)
class IncompleteDownloadError(DiagnosticPipError):
"""Raised when the downloader receives fewer bytes than advertised
in the Content-Length header."""
reference = "incomplete-download"
def __init__(self, download: _FileDownload) -> None:
# Dodge circular import.
from pip._internal.utils.misc import format_size
assert download.size is not None
download_status = (
f"{format_size(download.bytes_received)}/{format_size(download.size)}"
)
if download.reattempts:
retry_status = f"after {download.reattempts + 1} attempts "
hint = "Use --resume-retries to configure resume attempt limit."
else:
# Download retrying is not enabled.
retry_status = ""
hint = "Consider using --resume-retries to enable download resumption."
message = Text(
f"Download failed {retry_status}because not enough bytes "
f"were received ({download_status})"
)
super().__init__(
message=message,
context=f"URL: {download.link.redacted_url}",
hint_stmt=hint,
note_stmt="This is an issue with network connectivity, not pip.",
)
class ResolutionTooDeepError(DiagnosticPipError):
"""Raised when the dependency resolver exceeds the maximum recursion depth."""
reference = "resolution-too-deep"
def __init__(self) -> None:
super().__init__(
message="Dependency resolution exceeded maximum depth",
context=(
"Pip cannot resolve the current dependencies as the dependency graph "
"is too complex for pip to solve efficiently."
),
hint_stmt=(
"Try adding lower bounds to constrain your dependencies, "
"for example: 'package>=2.0.0' instead of just 'package'. "
),
link="https://pip.pypa.io/en/stable/topics/dependency-resolution/#handling-resolution-too-deep-errors",
)
class InstallWheelBuildError(DiagnosticPipError):
reference = "failed-wheel-build-for-install"
def __init__(self, failed: list[InstallRequirement]) -> None:
super().__init__(
message=(
"Failed to build installable wheels for some "
"pyproject.toml based projects"
),
context=", ".join(r.name for r in failed), # type: ignore
hint_stmt=None,
)