a
    ,e6                     @   s>  d Z ddlZddlZddlZddlZddlmZmZmZm	Z	m
Z
mZmZ ddlmZmZ ddlmZ ddlmZ ddlmZ ddlmZmZ ejZe
d	eZerd
ndZdZeddddddZejej ej!ej"ej#fZ$ej ejej!fZ%ee&Z'eedddZ(ee	e dddZ)eee	e f dddZ*G dd dZ+dS )a  Configuration management setup

Some terminology:
- name
  As written in config files.
- value
  Value associated with a name
- key
  Name combined with it's section (section.name)
- variant
  A single word describing where the configuration key-value pair came from
    N)AnyDictIterableListNewTypeOptionalTuple)ConfigurationError!ConfigurationFileCouldNotBeLoaded)appdirs)WINDOWS)	getLogger)
ensure_direnumKindzpip.inizpip.conf)versionhelpuserglobalZsiteenvzenv-var)USERGLOBALSITEENVENV_VAR)namereturnc                 C   s*   |   dd} | dr&| dd } | S )zAMake a name consistent regardless of source (environment or file)_-z--   N)lowerreplace
startswith)r    r#   :lib/python3.9/site-packages/pip/_internal/configuration.py_normalize_name2   s    
r%   c                 C   s&   d| vrd | }t|| ddS )N.zbKey does not contain dot separated section and key. Perhaps you wanted to use 'global.{}' instead?   )formatr	   split)r   Zerror_messager#   r#   r$   _disassemble_key:   s    r*   r   c                  C   st   dd t dD } tjtjt}tjtjdt	r<dndt}tjt 
dt}tj| tj|gtj||giS )Nc                 S   s   g | ]}t j|tqS r#   )ospathjoinCONFIG_BASENAME).0r-   r#   r#   r$   
<listcomp>E   s   z+get_configuration_files.<locals>.<listcomp>Zpip~z.pip)r   Zsite_config_dirsr,   r-   r.   sysprefixr/   
expanduserr   Zuser_config_dirkindsr   r   r   )Zglobal_config_filesZsite_config_fileZlegacy_config_fileZnew_config_filer#   r#   r$   get_configuration_filesD   s    


r7   c                       s  e Zd ZdZd6eee dd fddZddddZee	 dd	d
Z
eee	ef  dddZe	edddZe	eddddZe	ddddZddddZddddZeee	ef dddZddddZee	edddZe	ed d!d"Zddd#d$Ze	eee	ef  ee	ef d%d&d'Zeee	e	f  dd(d)Zeeeee	 f  dd*d+Zeee	ef d,d-d.Z ee	ef dd/d0Z!e	edd1d2d3Z"e	dd4d5Z#  Z$S )7Configurationa  Handles management of configuration.

    Provides an interface to accessing and managing configuration files.

    This class converts provides an API that takes "section.key-name" style
    keys and stores the value associated with it as "key-name" under the
    section "section".

    This allows for a clean interface wherein the both the section and the
    key-name are preserved in an easy to manage form in the configuration files
    and the data stored is also nice.
    N)isolated	load_onlyr   c                    sj   t    |d ur4|tvr4tddttt|| _|| _	dd t
D | _dd t
D | _g | _d S )Nz5Got invalid value for load_only - should be one of {}z, c                 S   s   i | ]
}|g qS r#   r#   r0   variantr#   r#   r$   
<dictcomp>r   s   z*Configuration.__init__.<locals>.<dictcomp>c                 S   s   i | ]
}|i qS r#   r#   r;   r#   r#   r$   r=   u   s   )super__init__VALID_LOAD_ONLYr	   r(   r.   mapreprr9   r:   OVERRIDE_ORDER_parsers_config_modified_parsers)selfr9   r:   	__class__r#   r$   r?   e   s     
zConfiguration.__init__r+   c                 C   s   |    | js|   dS )z<Loads configuration from configuration files and environmentN)_load_config_filesr9   _load_environment_varsrG   r#   r#   r$   loadz   s    zConfiguration.loadc                 C   s:   | j dusJ dz|  d W S  ty4   Y dS 0 dS )z7Returns the file with highest priority in configurationNz)Need to be specified a file to be editingr   )r:   _get_parser_to_modify
IndexErrorrL   r#   r#   r$   get_file_to_edit   s
    zConfiguration.get_file_to_editc                 C   s
   | j  S )z`Returns key-value pairs like dict.items() representing the loaded
        configuration
        )_dictionaryitemsrL   r#   r#   r$   rR      s    zConfiguration.items)keyr   c                 C   sF   |}t |}z| j| W S  ty@   t| td| Y n0 dS )z#Get a value from the configuration.No such key - N)r%   rQ   KeyErrorr*   r	   )rG   rS   orig_keyr#   r#   r$   	get_value   s    zConfiguration.get_value)rS   valuer   c                 C   s|   t |}|   | jsJ |  \}}|dur\t|\}}||sN|| |||| || j| j |< | 	|| dS )z$Modify a value in the configuration.N)
r%   _ensure_have_load_onlyr:   rN   r*   has_sectionZadd_sectionsetrE   _mark_as_modified)rG   rS   rX   fnameparsersectionr   r#   r#   r$   	set_value   s    


zConfiguration.set_valuec                 C   s   |}t |}|   | jsJ || j| j vr<td| |  \}}|durt|\}}||rr|||sztd|	|s|
| | || | j| j |= dS )z#Unset a value in the configuration.rT   Nz4Fatal Internal error [id=1]. Please report as a bug.)r%   rY   r:   rE   r	   rN   r*   rZ   Zremove_optionrR   Zremove_sectionr\   )rG   rS   rV   r]   r^   r_   r   r#   r#   r$   unset_value   s(    



zConfiguration.unset_valuec                 C   s   |    | jD ]\}}td| ttj| z8t|d}|	| W d   n1 s^0    Y  W q t
y } z td| d| W Y d}~qd}~0 0 qdS )z!Save the current in-memory state.zWriting to %swNz:An error occurred while writing to the configuration file z: )rY   rF   loggerinfor   r,   r-   dirnameopenwriteOSErrorr	   )rG   r]   r^   ferrorr#   r#   r$   save   s    ,zConfiguration.savec                 C   s$   | j d u rtdtd| j  d S )Nz'Needed a specific file to be modifying.z$Will be working with %s variant only)r:   r	   rc   debugrL   r#   r#   r$   rY      s    
z$Configuration._ensure_have_load_onlyc                 C   s"   i }t D ]}|| j|  q|S )z3A dictionary representing the loaded configuration.)rC   updaterE   )rG   Zretvalr<   r#   r#   r$   rQ      s    zConfiguration._dictionaryc                 C   s   t |  }|tj dd tjgkr4td dS | D ]V\}}|D ]H}| j	durp|| j	krptd|| qH| 
||}| j| ||f qHq<dS )z,Loads configuration from configuration filesr   r'   zZSkipping loading configuration files due to environment's PIP_CONFIG_FILE being os.devnullNz Skipping file '%s' (variant: %s))dictiter_config_filesr6   r   r,   devnullrc   rl   rR   r:   
_load_filerD   append)rG   config_filesr<   filesr]   r^   r#   r#   r$   rJ      s    z Configuration._load_config_files)r<   r]   r   c                 C   sL   t d|| | |}| D ]&}||}| j| | || q |S )Nz'For variant '%s', will try loading '%s')rc   verbose_construct_parserZsectionsrR   rE   rm   _normalized_keys)rG   r<   r]   r^   r_   rR   r#   r#   r$   rq     s    

zConfiguration._load_file)r]   r   c              
   C   s   t  }tj|rtd}z|j||d W nT tyV   t	d| d|dY n0 t j
y } zt	|dW Y d }~n
d }~0 0 |S )NF)encodingzcontains invalid z characters)reasonr]   )rj   )configparserRawConfigParserr,   r-   existslocalegetpreferredencodingreadUnicodeDecodeErrorr
   Error)rG   r]   r^   Zlocale_encodingrj   r#   r#   r$   rv     s    


 zConfiguration._construct_parserc                 C   s"   | j tj | d|   dS )z.Loads configuration from environment variablesz:env:N)rE   r6   r   rm   rw   get_environ_varsrL   r#   r#   r$   rK   *  s    z$Configuration._load_environment_vars)r_   rR   r   c                 C   s.   i }|D ] \}}|d t | }|||< q|S )zNormalizes items to construct a dictionary with normalized keys.

        This routine is where the names become keys and are made the same
        regardless of source - configuration files or environment.
        r&   )r%   )rG   r_   rR   Z
normalizedr   valrS   r#   r#   r$   rw   0  s
    
zConfiguration._normalized_keysc                 c   sD   t j D ]4\}}|dr
|dd  }|tvr
||fV  q
dS )z@Returns a generator with all environmental vars with prefix PIP_ZPIP_   N)r,   environrR   r"   r    ENV_NAMES_IGNORED)rG   rS   r   r   r#   r#   r$   r   >  s
    
zConfiguration.get_environ_varsc                 c   s   t jdd}|dur&tj|gfV  ntjg fV  t }tj|tj fV  | j ob|o`t j	| }|rztj
|tj
 fV  tj|tj fV  dS )zYields variant and configuration files associated with it.

        This should be treated like items of a dictionary.
        ZPIP_CONFIG_FILEN)r,   r   getr6   r   r7   r   r9   r-   r|   r   r   )rG   Zconfig_filers   Zshould_load_user_configr#   r#   r$   ro   G  s    zConfiguration.iter_config_files)r<   r   c                 C   s
   | j | S )z#Get values present in a config file)rE   )rG   r<   r#   r#   r$   get_values_in_confige  s    z"Configuration.get_values_in_configc                 C   s*   | j s
J | j| j  }|s"td|d S )Nz4Fatal Internal error [id=2]. Please report as a bug.)r:   rD   r	   )rG   Zparsersr#   r#   r$   rN   i  s    
z#Configuration._get_parser_to_modify)r]   r^   r   c                 C   s"   ||f}|| j vr| j | d S )N)rF   rr   )rG   r]   r^   Zfile_parser_tupler#   r#   r$   r\   w  s    
zConfiguration._mark_as_modifiedc                 C   s   | j j d| jdS )N())rI   __name__rQ   rL   r#   r#   r$   __repr__|  s    zConfiguration.__repr__)N)%r   
__module____qualname____doc__boolr   r   r?   rM   strrP   r   r   r   rR   rW   r`   ra   rk   rY   propertyr   rQ   rJ   r{   rq   rv   rK   rw   r   r   ro   r   rN   r\   r   __classcell__r#   r#   rH   r$   r8   W   s2   	

	r8   ),r   rz   r}   r,   r3   typingr   r   r   r   r   r   r   Zpip._internal.exceptionsr	   r
   Zpip._internal.utilsr   Zpip._internal.utils.compatr   Zpip._internal.utils.loggingr   Zpip._internal.utils.miscr   r   r{   r   r   r/   r   r6   r   r   r   r   r   rC   r@   r   rc   r%   r*   r7   r8   r#   r#   r#   r$   <module>   s8   $

