o
    ip                     @  s|   d dl mZ d dlmZmZ d dlmZmZ h dZd d
dZ	d!ddZ
d"ddZd#ddZeG dd dZd$ddZdS )%    )annotations)	dataclassfield)ListOptional>   {}()[]valuestr
field_namereturnNonec                 C  s<   | D ]}t |dk st |dks|tv rt| dqdS )zEnsure value contains only printable ASCII without spaces or braces.

    This mirrors the constraints enforced by other Redis clients for values that
    will appear in CLIENT LIST / CLIENT INFO output.
    !   ~   zG must not contain spaces, newlines, non-printable characters, or bracesN)ord_BRACES
ValueError)r   r   ch r   E/home/ubuntu/.local/lib/python3.10/site-packages/redis/driver_info.py_validate_no_invalid_chars	   s    r   namec                 C  s*   ddl }t| d |d| stddS )ao  Validate an upstream driver name.

    The name should look like a typical Python distribution or package name,
    following a simplified form of PEP 503 normalisation rules:

    * start with a lowercase ASCII letter
    * contain only lowercase letters, digits, hyphens and underscores

    Examples of valid names: ``"django-redis"``, ``"celery"``, ``"rq"``.
    r   NzDriver namez^[a-z][a-z0-9_-]*$zUpstream driver name must use a Python package-style name: start with a lowercase letter and contain only lowercase letters, digits, hyphens, and underscores (e.g., 'django-redis').)rer   matchr   )r   r   r   r   r   _validate_driver_name   s   
r   versionc                 C  s   t | d d S )NzDriver version)r   )r   r   r   r   _validate_driver_version/      r    driver_namedriver_versionc                 C  s   |  d| S )N_vr   )r"   r#   r   r   r   _format_driver_entry3   r!   r%   c                   @  sj   e Zd ZU dZdZded< dZded< eedZ	d	ed
< dd Z
edddZdddZedddZdS )
DriverInfoa  Driver information used to build the CLIENT SETINFO LIB-NAME and LIB-VER values.

    This class consolidates all driver metadata (redis-py version and upstream drivers)
    into a single object that is propagated through connection pools and connections.

    The formatted name follows the pattern::

        name(driver1_vVersion1;driver2_vVersion2)

    Parameters
    ----------
    name : str, optional
        The base library name (default: "redis-py")
    lib_version : str, optional
        The redis-py library version. If None, the version will be determined
        automatically from the installed package.

    Examples
    --------
    >>> info = DriverInfo()
    >>> info.formatted_name
    'redis-py'

    >>> info = DriverInfo().add_upstream_driver("django-redis", "5.4.0")
    >>> info.formatted_name
    'redis-py(django-redis_v5.4.0)'

    >>> info = DriverInfo(lib_version="5.0.0")
    >>> info.lib_version
    '5.0.0'
    redis-pyr   r   NOptional[str]lib_version)default_factory	List[str]	_upstreamc                 C  s&   | j du rddlm} | | _ dS dS )z'Initialize lib_version if not provided.Nr   get_lib_version)r)   redis.utilsr.   )selfr.   r   r   r   __post_init__]   s   
zDriverInfo.__post_init__r   c                 C  s
   t | jS )zuReturn a copy of the upstream driver entries.

        Each entry is in the form ``"driver-name_vversion"``.
        )listr,   r0   r   r   r   upstream_driversd   s   
zDriverInfo.upstream_driversr"   r#   'DriverInfo'c                 C  sL   |du rt d|du rt dt| t| t||}| jd| | S )zAdd an upstream driver to this instance and return self.

        The most recently added driver appears first in :pyattr:`formatted_name`.
        NzDriver name must not be NonezDriver version must not be Noner   )r   r   r    r%   r,   insert)r0   r"   r#   entryr   r   r   add_upstream_driverm   s   
zDriverInfo.add_upstream_driverc                 C  s&   | j s| jS | j dd| j  dS )zReturn the base name with upstream drivers encoded, if any.

        With no upstream drivers, this is just :pyattr:`name`. Otherwise::

            name(driver1_vX;driver2_vY)
        r	   ;r
   )r,   r   joinr3   r   r   r   formatted_name   s   	zDriverInfo.formatted_name)r   r+   )r"   r   r#   r   r   r5   )r   r   )__name__
__module____qualname____doc__r   __annotations__r)   r   r2   r,   r1   propertyr4   r8   r;   r   r   r   r   r&   7   s   
  
r&   driver_infoOptional[DriverInfo]lib_namer(   r)   c                 C  sF   | dur| S ddl m} |dur|nd}|dur|n| }t||dS )a  Resolve driver_info from parameters.

    If driver_info is provided, use it. Otherwise, create DriverInfo from
    lib_name and lib_version (using defaults if not provided).

    Parameters
    ----------
    driver_info : DriverInfo, optional
        The DriverInfo instance to use
    lib_name : str, optional
        The library name (default: "redis-py")
    lib_version : str, optional
        The library version (default: auto-detected)

    Returns
    -------
    DriverInfo
        The resolved DriverInfo instance
    Nr   r-   r'   )r   r)   )r/   r.   r&   )rB   rD   r)   r.   r   r   r   r   r   resolve_driver_info   s   rE   N)r   r   r   r   r   r   )r   r   r   r   )r   r   r   r   )r"   r   r#   r   r   r   )rB   rC   rD   r(   r)   r(   r   r&   )
__future__r   dataclassesr   r   typingr   r   r   r   r   r    r%   r&   rE   r   r   r   r   <module>   s    



X