a
    !f                     @   s  d Z ddlZddlZddlZddlZddlZddlZddlZddl	Z	ddl
Z
ddlZddlZddlZddlZddlmZ ddlmZ ddlmZ ddlmZ ddlmZ ddlmZ dd	lmZ dd
lmZ ddlmZ ddlmZ ddlmZ ddlmZ ddlmZ ddlm Z  ddlm!Z! ddlm"Z" ddlm#Z# ddlm$Z$ ddlm%Z% ddlm&Z& ddlm'Z' ddlm(Z( ddl)m*Z* ddl)m+Z+ ddl)m,Z, ddl-Z.ddl/Z.ddl0Z.ddl1m2Z2 ddl1m3Z3 ddl4m5Z5 dd l-m6Z6 dd!l-m7Z7 dd"l8m9Z9 dd#l:m;Z; dd$l:m<Z< dd%l=m>Z> dd&l=m?Z? dd'l@mAZA dd(l@mBZB dd)l@mCZC dd*l@mDZD dd+l@mEZE dd,l@mFZF dd-lGmHZH dd.lImJZJ dd/lImKZK e'rdd0lLmMZM dd1lNmOZO dd2lPmQZQ eRZSe*d3ZTe+d3ZUe;G d4d5 d5ejVZWG d6d7 d7eXZYe.jZj[e\d8d9d:Z]de!e(e e^ d;f  e!e"e(e^eSf   e(e_eWf d<d=d>Z`e_d?d@dAZaG dBdC dCZbe^e^e^dDdEdFZce^e^e^dDdGdHZddIZeeedJdKdLdMdNdOdPdQdRdSdTdUdVdWdXdYdZd[d\d]d^d_d`dagejfdbkrdcddgng deR  ZgehegZieijdf eijdg de!e e^  e!e"e(e^eSf   dhd<didjZkdkd?dldmZlde!e(e e^ d;f  e!e"e(e^eSf   dhd<dndoZmeedpdqdrZnee^e%e^dsf ee^e\f dtdudvZoe;G dwdk dke,Zpe(dejqe^e"e^ f e e^ dxdydzZre^dd{d|d}ZsG d~d dZtet Zuee^ ee^ dddZve;G ddh dhZwe\d?ddZxdewe!e$ e9dddZye^e\dddZzedde^e\e%de^e&e{ e^e_f dddZ|e^e&e{ dddZ}ee^ ee^ ddddZ~dS )z:Command line options, ini-file and conftest.py processing.    N)	lru_cache)Path)dedent)FunctionType)TracebackType)Any)Callable)cast)Dict)	Generator)IO)Iterable)Iterator)List)Optional)Sequence)Set)TextIO)Tuple)Type)TYPE_CHECKING)Union)HookimplMarker)HookspecMarker)PluginManager   )	PrintHelp)
UsageError)determine_setup)ExceptionInfo)filter_traceback)TerminalWriter)final)importlib_metadata)fail)Skipped)absolutepath)bestrelpath)import_path)
ImportMode)resolve_package_path)safe_exists)Stash)PytestConfigWarning)warn_explicit_for)_TracebackStyle)TerminalReporter)Argumentpytestc                   @   s(   e Zd ZdZdZdZdZdZdZdZ	dS )	ExitCodezEncodes the valid exit codes by pytest.

    Currently users and plugins may supply other exit codes as well.

    .. versionadded:: 5.0
    r   r               N)
__name__
__module____qualname____doc__OKZTESTS_FAILEDZINTERRUPTEDINTERNAL_ERRORUSAGE_ERRORZNO_TESTS_COLLECTED r?   r?   X/var/www/html/python-backend/venv/lib/python3.9/site-packages/_pytest/config/__init__.pyr3   U   s   r3   c                       sB   e Zd Zeeee eef dd fddZe	dddZ
  ZS )ConftestImportFailureN)pathexcinforeturnc                    s   t  || || _|| _d S N)super__init__rB   rC   )selfrB   rC   	__class__r?   r@   rG   m   s    zConftestImportFailure.__init__rD   c                 C   s   d | jd j| jd | jS )Nz{}: {} (from {})r   r   )formatrC   r8   rB   rH   r?   r?   r@   __str__v   s    zConftestImportFailure.__str__)r8   r9   r:   r   r   r   	Exceptionr   rG   strrN   __classcell__r?   r?   rI   r@   rA   l   s
   	rA   )entryrD   c                 C   s   t | odt| jtjvS )zFilter tracebacks entries which point to pytest internals or importlib.

    Make a special case for importlib because we use it to import test modules and conftest files
    in _pytest.pathlib.import_path.
    	importlib)r    rP   rB   splitossep)rR   r?   r?   r@   ,filter_traceback_for_conftest_import_failure|   s    rW   zos.PathLike[str])argspluginsrD   c              
   C   s  z"zt | |}W n ty } zt|j}ttj}|jd|j	 ddd |j
t|_
|j
rr|jdddn| }t|}| D ]}|j| dd qtjW  Y d}~W S d}~0 0 zV|jj|d	}	zt|	W W |  W S  ty
   |	 Y W |  W S 0 W |  n
|  0 W nZ ty~ } z@ttj}|jD ]}
|jd
|
 ddd qFtjW  Y d}~S d}~0 0 dS )aL  Perform an in-process test run.

    :param args:
        List of command line arguments. If `None` or not given, defaults to reading
        arguments directly from the process command line (:data:`sys.argv`).
    :param plugins: List of plugin objects to be auto-registered during initialization.

    :returns: An exit code.
    z$ImportError while loading conftest 'z'.T)redshortF)stylechainNconfigzERROR: 
)_prepareconfigrA   r   Zfrom_exc_inforC   r!   sysstderrlinerB   	tracebackfilterrW   getreprZexconlyrP   
splitlinesrstripr3   r>   hookZpytest_cmdline_main_ensure_unconfigure
ValueErrorr   rX   )rX   rY   r_   eexc_infotwZexc_reprZformatted_tbrd   retmsgr?   r?   r@   main   sH    



rr   rK   c                  C   sR   zt  } tj  | W S  tyL   ttjtj}t	|tj
  Y dS 0 dS )zoThe CLI entry point of pytest.

    This function is not meant for programmable use; use `main()` instead.
    r   N)rr   rb   stdoutflushBrokenPipeErrorrU   opendevnullO_WRONLYdup2fileno)coderw   r?   r?   r@   console_main   s    
r|   c                   @   s   e Zd ZeeZdS )cmdlineN)r8   r9   r:   staticmethodrr   r?   r?   r?   r@   r}      s   r}   )rB   optnamerD   c                 C   s"   t j| rt| d|  | S )ztArgparse type validator for filename arguments.

    :path: Path of filename.
    :optname: Name of the option.
    z must be a filename, given: rU   rB   isdirr   rB   r   r?   r?   r@   filename_arg   s    r   c                 C   s"   t j| st| d|  | S )zvArgparse type validator for directory arguments.

    :path: Path of directory.
    :optname: Name of the option.
    z must be a directory, given: r   r   r?   r?   r@   directory_arg   s    r   )markrr   runnerZfixturesZ
helpconfigpythonZterminal	debuggingZunittestcaptureskippingZ
legacypathZtmpdirZmonkeypatchZrecwarnZpastebinnose	assertionZjunitxmldoctestcacheproviderZfreeze_supportZ	setuponlyZ	setupplanstepwisewarningsloggingZreportsZpython_path)r5      ZunraisableexceptionZthreadexceptionfaulthandlerZpytesterZpytester_assertionsConfigc                 C   sT   t  }t|tj| pd|t dd}| d ur<|j| dd tD ]}|| q@|S )Nr?   rX   rY   dirinvocation_paramsTexclude_only)PytestPluginManagerr   InvocationParamsr   cwdconsider_preparsedefault_pluginsimport_plugin)rX   rY   pluginmanagerr_   specr?   r?   r@   
get_config  s    	r   r   c                   C   s   t  jS )zObtain a new instance of the
    :py:class:`pytest.PytestPluginManager`, with default plugins
    already loaded.

    This function can be used by integration with other tools, like hooking
    into pytest to run tests into an IDE.
    )r   r   r?   r?   r?   r@   get_plugin_manager)  s    r   c                 C   s   | d u rt jdd  } n<t| tjr2t| g} n"t| tsTd}t|| t	| t
| |}|j}zD|r|D ]$}t|tr|| qn|| qn|jj|| d}|W S  ty   |   Y n0 d S )Nr   zG`args` parameter expected to be a list of strings, got: {!r} (type: {}))r   rX   )rb   argv
isinstancerU   PathLikefspathlist	TypeErrorrL   typer   r   rP   consider_pluginargregisterrj   pytest_cmdline_parseBaseExceptionrk   )rX   rY   rq   r_   r   pluginr?   r?   r@   ra   4  s.    


ra   rB   rD   c                 C   s   |   r| jS | S dS )z<Get the directory of a path - itself if already a directory.N)is_fileparent)rB   r?   r?   r@   _get_directoryT  s    r   .)method	hook_type	opt_namesrD   c           
      C   s   t rt| sJ dd t| dg D }g }i }|D ]`}t| |t}|turj|| d|  d||< q4||v r|| d d||< q4d||< q4|rd|}tjj	j
|| j|d	}	ttt| |	 |S )
Nc                 S   s   h | ]
}|j qS r?   name).0mr?   r?   r@   	<setcomp>d      z)_get_legacy_hook_marks.<locals>.<setcomp>Z
pytestmark=Tz=TrueF, )r   fullname	hook_opts)r   inspect	isroutinegetattrAttributeErrorappendjoin_pytest
deprecatedZHOOK_LEGACY_MARKINGrL   r:   r.   r	   r   )
r   r   r   Zknown_marksZ	must_warnoptsopt_nameZopt_attrr   messager?   r?   r@   _get_legacy_hook_marks\  s.    



r   c                       s  e Zd ZdZdd fddZeed fddZed	 fd
dZdCee	e e	e d fddZ
ed	ddZeedddZdddddZeeeef  eeee	e eeef ddddZeedddZeeeef edddd Zeeeef eeej d!d"d#Zeeeeef eeejef d$d%d&Zeeeef eejd'd(d)Zejedd*d+d,Zd-d.ee edd/d0d1Zedd2d3d4Zejdd5d6d7Z ddd8d9Z!ejdd:d;d<Z"edejeee f dd=d>d?Z#dDeedd@dAdBZ$  Z%S )Er   a;  A :py:class:`pluggy.PluginManager <pluggy.PluginManager>` with
    additional pytest-specific functionality:

    * Loading plugins from the command line, ``PYTEST_PLUGINS`` env variable and
      ``pytest_plugins`` global variables found in plugins being loaded.
    * ``conftest.py`` loading during start-up.
    NrK   c                    s   dd l }t d t | _i | _d | _d| _tdt	| _	t | _
g | _| |j | |  tjdrtj}t|dd}z tt| |jd|d	}W n ty   Y n0 | jj|j |   |j  | _!d| _"d S )
Nr   r2   F   ZPYTEST_DEBUGencodingutf8r   )mode	bufferingr   )#_pytest.assertionrF   rG   set_conftest_plugins_dirpath2confmods_confcutdir_noconftestr   r   Z_duplicatepathsskipped_pluginsZadd_hookspecshookspecr   rU   environgetrb   rc   r   rv   duprz   r   rO   tracerootZ	setwriterwriteZenable_tracingr   ZDummyRewriteHookrewrite_hook_configured)rH   r   errr   rI   r?   r@   rG     s6    

zPytestPluginManager.__init__)r   r   c                    sX   | dsd S |dkrd S t ||}|d ur4|S t||}t|sLd S t|ddS )Npytest_pytest_pluginsimpl)ZtryfirsttrylastZoptionalhookhookwrapper)
startswithrF   parse_hookimpl_optsr   r   r   r   )rH   r   r   r   r   rI   r?   r@   r     s    


z'PytestPluginManager.parse_hookimpl_optsr   c                    s:   t  ||}|d u r6t||}|dr6t|dd}|S )Nr   r   )ZfirstresultZhistoric)rF   parse_hookspec_optsr   r   r   )rH   Zmodule_or_classr   r   r   rI   r?   r@   r     s    

z'PytestPluginManager.parse_hookspec_opts)r   r   rD   c              	      sp   |t jjv r,ttd|dd d S t 	||}|rl| j
jjt|| dd t|tjrl| | |S )NzQ{} plugin has been merged into the core, please remove it from your requirements._-)r   managerkwargs)r   r   ZDEPRECATED_EXTERNAL_PLUGINSr   warnr-   rL   replacerF   r   rj   Zpytest_plugin_registeredcall_historicdictr   types
ModuleTypeconsider_module)rH   r   r   rp   rI   r?   r@   r     s"    


zPytestPluginManager.registerc                 C   s   |  |}|S rE   )
get_plugin)rH   r   r   r?   r?   r@   	getplugin  s    
zPytestPluginManager.getpluginr   rD   c                 C   s   t | |S )z:Return whether a plugin with the given name is registered.)boolr   )rH   r   r?   r?   r@   	hasplugin  s    zPytestPluginManager.haspluginr   )r_   rD   c                 C   s"   | dd | dd d| _dS ):meta private:markersztryfirst: mark a hook implementation function such that the plugin machinery will try to call it first/as early as possible. DEPRECATED, use @pytest.hookimpl(tryfirst=True) instead.ztrylast: mark a hook implementation function such that the plugin machinery will try to call it last/as late as possible. DEPRECATED, use @pytest.hookimpl(trylast=True) instead.TN)addinivalue_liner   )rH   r_   r?   r?   r@   pytest_configure  s    z$PytestPluginManager.pytest_configure)rX   pyargs
noconftestrootpath
confcutdir
importmoderD   c                 C   s   t  }|rt|| nd| _|| _|| _d}|D ]P}	t|	}
|
d}|dkr\|
d| }
t||
 }t|r2| 	||| d}q2|s| 	||| dS )a`  Load initial conftest files given a preparsed "namespace".

        As conftest files may add their own command line options which have
        arguments ('--my-opt somepath') we might get some false positives.
        All builtin and 3rd party plugins will have been loaded, however, so
        common options will not confuse our logic here.
        NFz::T)
r   r   r&   r   r   _using_pyargsrP   findr+   _try_load_conftest)rH   rX   r  r  r  r  r  currentZfoundanchorZintitial_pathrB   ianchorr?   r?   r@   _set_initial_conftests  s     
z*PytestPluginManager._set_initial_conftestsr   c                 C   s   | j du rdS || j jvS )z`Whether a path is within the confcutdir.

        When false, should not load conftest.
        NT)r   parents)rH   rB   r?   r?   r@   _is_in_confcutdir8  s    
z%PytestPluginManager._is_in_confcutdir)r  r  r  rD   c                 C   s@   |  ||| | r<|dD ]}| r |  ||| q d S )Nztest*)_getconftestmodulesis_dirglob)rH   r  r  r  xr?   r?   r@   r	  A  s
    z&PytestPluginManager._try_load_conftest)rB   r  r  rD   c           
      C   s   | j r
g S | |}| j|}|d ur,|S g }t|g|jR D ]6}| |rB|d }| rB| |||}	|	|	 qB|| j|< |S )Nzconftest.py)
r   r   r   r   reversedr  r  r   _importconftestr   )
rH   rB   r  r  	directoryZexisting_clistZclistr   conftestpathmodr?   r?   r@   r  K  s    


z'PytestPluginManager._getconftestmodules)r   rB   r  r  rD   c              	   C   sV   | j |||d}t|D ]0}z|t||fW   S  tyF   Y qY q0 qt|d S )N)r  )r  r  r   r   KeyError)rH   r   rB   r  r  modulesr  r?   r?   r@   _rget_with_confmodf  s    z&PytestPluginManager._rget_with_confmod)r  r  r  rD   c              
   C   s"  |  t|}|d ur"ttj|S t|}|d u r<t|j zt|||d}W nN t	y } z6|j
d uslJ t|||j
f}t|||W Y d }~n
d }~0 0 | || | j| |j}	|	| jv r| j D ]0\}
}|	|
jv s|
|	kr||vsJ || q| d| | | |S )N)r   r   zloading conftestmodule )r   rP   r	   r   r   r*   _ensure_removed_sysmodulestemr(   rO   __traceback__r   rA   _check_non_top_pytest_pluginsr   addr   r   itemsr  r   r   consider_conftest)rH   r  r  r  existingpkgpathr  rm   rn   dirpathrB   modsr?   r?   r@   r  u  s.    
"
z#PytestPluginManager._importconftest)r  r  rD   c                 C   s4   t |dr0| jr0| js0d}t||| jdd d S )Nr   af  Defining 'pytest_plugins' in a non-top-level conftest is no longer supported:
It affects the entire test suite instead of just below the conftest as expected.
  {}
Please move it to a top level conftest file at the rootdir:
  {}
For more information, visit:
  https://docs.pytest.org/en/stable/deprecations.html#pytest-plugins-in-non-top-level-conftest-filesF)Zpytrace)hasattrr   r  r$   rL   r   )rH   r  r  rq   r?   r?   r@   r    s    	z1PytestPluginManager._check_non_top_pytest_pluginsFr   )rX   r   rD   c                C   s   d}t |}||k r|| }|d7 }t|tr|dkrbz|| }W n tyV   Y dS 0 |d7 }n|dr|dd }nq| }|r|dsq| | qdS )r   r   r   z-pNr4   no:)lenr   rP   
IndexErrorr   stripr   )rH   rX   r   r  noptZpargr?   r?   r@   r     s&    


z%PytestPluginManager.consider_preparse)argrD   c                 C   s   | drj|dd }|tv r*td| |dkrF| d | d | | | ds| d|  nX|}| j|d	du r| j|= | ds| jd| d	du r| jd| = | j|d
d dS )r   r(  r5   Nzplugin %s cannot be disabledr   r   Zpytest_stepwiser   r  T)consider_entry_points)r   essential_pluginsr   Zset_blockedZ_name2pluginr   r   )rH   r.  r   r?   r?   r@   r     s"    





z&PytestPluginManager.consider_pluginarg)conftestmodulerD   c                 C   s   | j ||jd dS )r   r   N)r   __file__)rH   r1  r?   r?   r@   r"    s    z%PytestPluginManager.consider_conftestc                 C   s   |  tjd dS )r   ZPYTEST_PLUGINSN)_import_plugin_specsrU   r   r   rM   r?   r?   r@   consider_env  s    z PytestPluginManager.consider_env)r  rD   c                 C   s   |  t|dg  dS )r   r   N)r3  r   )rH   r  r?   r?   r@   r     s    z#PytestPluginManager.consider_module)r   rD   c                 C   s    t |}|D ]}| | qd S rE   )_get_plugin_specs_as_listr   )rH   r   rY   Zimport_specr?   r?   r@   r3    s    z(PytestPluginManager._import_plugin_specs)modnamer/  rD   c              
   C   s  t |tsJ d| | |s.| |dur2dS |tv rBd| n|}| j| |rl| jd|d}|rldS zt| W n t	y } z0t	d| d|j
d  |j|W Y d}~nXd}~0  ty } z"| j||jpd	f W Y d}~n d}~0 0 tj| }| || dS )
zImport a plugin with ``modname``.

        If ``consider_entry_points`` is True, entry point names are also
        considered to find a plugin.
        z$module name as text required, got %rNz_pytest.pytest11r   zError importing plugin "z": r    )r   rP   
is_blockedr   builtin_pluginsr   mark_rewriteload_setuptools_entrypoints
__import__ImportErrorrX   with_tracebackr  r%   r   r   rq   rb   r  r   )rH   r6  r/  Z
importspecZloadedrm   r  r?   r?   r@   r     s2    
,
z!PytestPluginManager.import_plugin)N)F)&r8   r9   r:   r;   rG   _PluggyPluginrP   r   r   r   r   r   r   r   r   r   r   r   r)   r  r  r	  r   r   r  r   r   r  r  r  r   r   r"  r4  r   r3  r   rQ   r?   r?   rI   r@   r   |  sj   5 
%

!)specsrD   c                 C   s^   | du rg S t | tjrg S t | tr8| r4| dS g S t | tjjrNt| S t	d|  dS )z:Parse a plugins specification into a list of plugin names.N,zYPlugins may be specified as a sequence or a ','-separated string of plugin names. Got: %r)
r   r   r   rP   rT   collectionsabcr   r   r   )rA  r?   r?   r@   r5    s    
r5  )r6  rD   c                 C   s$   zt j| = W n ty   Y n0 d S rE   )rb   r  r  )r6  r?   r?   r@   r  0  s    r  c                   @   s   e Zd Zdd ZdS )Notsetc                 C   s   dS )Nz<NOTSET>r?   rM   r?   r?   r@   __repr__8  s    zNotset.__repr__N)r8   r9   r:   rF  r?   r?   r?   r@   rE  7  s   rE  )package_filesrD   c                 c   s   t | } d}| D ]z}d|vo$|d}|ddko<|d}|rptj|\}}|dkr|dsd}|V  q|rtj|}d}|V  q|sg }| D ].}|d}	d	|	dd	 }
|
r|
|
 q|rt|E d	H  d	S )
aM  Given an iterable of file names in a source distribution, return the "names" that should
    be marked for assertion rewrite.

    For example the package "pytest_mock/__init__.py" should be added as "pytest_mock" in
    the assertion rewrite mechanism.

    This function has to deal with dist-info based distributions and egg based distributions
    (which are still very much in use for "editable" installs).

    Here are the file names as seen in a dist-info based distribution:

        pytest_mock/__init__.py
        pytest_mock/_version.py
        pytest_mock/plugin.py
        pytest_mock.egg-info/PKG-INFO

    Here are the file names as seen in an egg based distribution:

        src/pytest_mock/__init__.py
        src/pytest_mock/_version.py
        src/pytest_mock/plugin.py
        src/pytest_mock.egg-info/PKG-INFO
        LICENSE
        setup.py

    We have to take in account those two distribution flavors in order to determine which
    names should be considered for assertion rewriting.

    More information:
        https://github.com/pytest-dev/pytest-mock/issues/167
    F/z.pyr   z__init__.pysetupZ__editable__TN)r   endswithcountrU   rB   splitextr   dirnamerT   r   r   _iter_rewritable_modules)rG  Z	seen_somefnZis_simple_module
is_packagemodule_namer   package_nameZnew_package_filespartsZnew_fnr?   r?   r@   rN  ?  s.     
rN  c                	   @   sB  e Zd ZdZeejddG dd dZG dd dej	Z
dd	eee dd
ddZeedddZeee dddZeg df ddddZddddZddddZedddZeee d dddZdpee eej dddd Zeed!d"d#Z e!d dd$d%Z"d&dd'd(d)Z#e$dd*d dd+d,d-Z%e&e dd.d/d0Z'e&e dd.d1d2Z(ddd3d4Z)ee eee d5d6d7Z*ee ee ee eee+e,ee e
f d8d9d:Z-dqee e+dd;d<d=Z.e$dd>e/d? dd@dAZ0dddBdCZ1dddDdEZ2dddFdGZ3eddHdIdJZ4ee ddKdLZ5dree e+dd;dMdNZ6e7e8ddOdPdQZ9eeddRdSdTZ:edUdVdWZ;eee<eee f dXdYdZZ=edUd[d\Z>eeeeee  d]d^d_Z?eee d`dadbZ@eAdcfee+dddedfZBdsedUdgdhZCdtedUdidjZDeddkdldmZEdddndoZFdS )ur   a  Access to configuration values, pluginmanager and plugin hooks.

    :param PytestPluginManager pluginmanager:
        A pytest PluginManager.

    :param InvocationParams invocation_params:
        Object containing parameters regarding the :func:`pytest.main`
        invocation.
    T)frozenc                   @   sj   e Zd ZU dZeedf ed< eee	ee
f   ed< eed< ee eee	ee
f   edddd	ZdS )
zConfig.InvocationParamsa  Holds parameters passed during :func:`pytest.main`.

        The object attributes are read-only.

        .. versionadded:: 5.1

        .. note::

            Note that the environment variable ``PYTEST_ADDOPTS`` and the ``addopts``
            ini option are handled by pytest, not being included in the ``args`` attribute.

            Plugins accessing ``InvocationParams`` must be aware of that.
        .rX   rY   r   N)rX   rY   r   rD   c                C   s2   t | dt| t | d| t | d| d S )NrX   rY   r   )object__setattr__tuple)rH   rX   rY   r   r?   r?   r@   rG     s    z Config.InvocationParams.__init__)r8   r9   r:   r;   r   rP   __annotations__r   r   r   r@  r   r   rG   r?   r?   r?   r@   r     s   
r   c                   @   s(   e Zd ZdZe Ze Ze ZdS )zConfig.ArgsSourcezSIndicates the source of the test arguments.

        .. versionadded:: 7.2
        N)	r8   r9   r:   r;   enumautoARGSINCOVATION_DIR	TESTPATHSr?   r?   r?   r@   
ArgsSource  s   r^  Nr   )r   r   rD   c                C   s  ddl m}m} |d u r,| jdd t d}t | _|| _	|}|d| d| d| j
dd	| _|| _t | _| j| _dd
lm} | jjjd| _|| jj| _i | _d| _i | _g | _| j| d d| _| jjjt| j| jdd tj j!| _"g | _#t$rddl%m&} d | _'d S )Nr   )ParserFILE_OR_DIRr?   r   z%(prog)s [options] [z] [z] [...]T)usageZ
processoptZ	_ispytest)PathAwareHookProxyr_   ZpytestconfigF)parserr   r   r   )Cache)(
argparsingr_  r`  r   r   r   argparse	Namespaceoptionr   _processopt_parserr   r,   stash_storecompatrb  r   r   r   rj   	_inicache_override_ini	_opt2dest_cleanupr   r   Zpytest_addoptionr   r   r   r^  r[  args_sourcerX   r   Z_pytest.cacheproviderrd  cache)rH   r   r   r_  r`  Z_arb  rd  r?   r?   r@   rG     sB    


zConfig.__init__rK   c                 C   s   | j S )znThe path to the :ref:`rootdir <rootdir>`.

        :type: pathlib.Path

        .. versionadded:: 6.1
        )	_rootpathrM   r?   r?   r@   r    s    zConfig.rootpathc                 C   s   | j S )zThe path to the :ref:`configfile <configfiles>`.

        :type: Optional[pathlib.Path]

        .. versionadded:: 6.1
        )_inipathrM   r?   r?   r@   inipath	  s    zConfig.inipath)funcrD   c                 C   s   | j | dS )zxAdd a function to be called when the config object gets out of
        use (usually coinciding with pytest_unconfigure).N)rq  r   )rH   rw  r?   r?   r@   add_cleanup  s    zConfig.add_cleanupc                 C   s\   | j r
J d| _ t 0 td | jjjt| dd W d    n1 sN0    Y  d S )NTdefaultr^   r   )r   r   catch_warningssimplefilterrj   r   r   r   rM   r?   r?   r@   _do_configure  s
    


zConfig._do_configurec                 C   s@   | j r$d| _ | jj| d g | jj_| jr<| j }|  q$d S )NFr^   )r   rj   Zpytest_unconfigurer   Z_call_historyrq  pop)rH   Zfinr?   r?   r@   rk     s    

zConfig._ensure_unconfigurec                 C   s   | j d}|d usJ |jS )Nterminalreporter)r   r   Z_tw)rH   r~  r?   r?   r@   get_terminal_writer(  s
    zConfig.get_terminal_writer)r   rX   rD   c                 C   s   z|  | W nx ty   t| jdds2d|v rHddlm} ||  n8t| jddsfd|v sfd|v r| j   t	j
d	  Y n0 | S )
NversionFz	--versionr   )showversionhelpz--helpz-hz8
NOTE: displaying only minimal help due to UsageError.

)parser   r   rh  Z_pytest.helpconfigr  rj  Z
_getparser
print_helprb   rs   r   )rH   r   rX   r  r?   r?   r@   r   /  s$    
zConfig.pytest_cmdline_parse)rC   rh  rD   c                 C   s|   |rt |ddrd}nd}|jdt |dd|d}| jj||d}t|sxt|d	D ]}tj	d
|  tj
  qXd S )NZ	fulltraceFlongnativeT
showlocals)Zfuncargsr  r\   )excreprrC   r`   zINTERNALERROR> %s
)r   rg   rj   Zpytest_internalerroranyrP   rT   rb   rc   r   rt   )rH   rC   rh  r\   r  resrd   r?   r?   r@   notify_exceptionH  s    zConfig.notify_exception)nodeidrD   c                 C   s*   | j j| jkr&| j| }t| j j|}|S rE   )r   r   r  r'   )rH   r  fullpathr?   r?   r@   cwd_relative_nodeidZ  s    
zConfig.cwd_relative_nodeidc                 C   sB   t |}|jj| |j|dd |jjD ]}|j| q,|S )z$Constructor usable for subprocesses.Faddopts)r   rh  __dict__updater  rY   r   r   )clsoption_dictrX   r_   r  r?   r?   r@   fromdictargsa  s    zConfig.fromdictargsr1   )r-  rD   c                 C   sL   |j |j D ]}|j| j|< qt|drHt| j|jsHt| j|j|j d S )Nry  )_short_opts
_long_optsdestrp  r'  rh  setattrry  )rH   r-  r   r?   r?   r@   ri  k  s
    
zConfig._processopt)r   )early_configrD   c                 C   s\   |j |jj|jj|d|jj|jdd\}}| jj	||jj|jj
|j|jj|jjd d S )N	testpathsFrX   r  r  invocation_dirr  r   )rX   r  r  r  r  r  )_decide_argsknown_args_namespacefile_or_dirr  getinir   r   r  r   r  r  r  r  )rH   r  rX   rr  r?   r?   r@   pytest_load_initial_conftestss  s     
z$Config.pytest_load_initial_conftests)rX   rD   c                 C   s   | j j|t| jd\}}t|j|j| |jp2d | d\}}}|| _|| _	|| _
t| j| j jd< t| j| j jd< | j ddd | j dd	 | j jd
ddg d |jpd| _d S )N	namespace)Zrootdir_cmd_argr_   rootdirZinifiler  zExtra command line optionsrX   
minversionz!Minimally required pytest versionrequired_pluginsz.Plugins that must be present for pytest to run)r   ry  r?   )rj  parse_known_and_unknown_argscopyrh  r   Zinifilenamer  r  rt  ru  inicfgrP   r  Z
extra_inforv  ZaddiniZoverride_iniro  )rH   rX   nsunknown_argsr  rv  r  r?   r?   r@   _initini  s.    
zConfig._initinic                 C   sl   | j |\}}t|dd}|dkr^ddl}z|j| }W n tyR   d}Y n0 | | | | dS )zInstall the PEP 302 import hook if using assertion rewriting.

        Needs to parse the --assert=<mode> option from the commandline
        and find all the installed plugins to mark them for rewriting
        by the importhook.
        Z
assertmodeplainZrewriter   N)	rj  r  r   r   r   Zinstall_importhookSystemError_mark_plugins_for_rewrite_warn_about_missing_assertion)rH   rX   r  r  r   r   rj   r?   r?   r@   _consider_importhook  s    

zConfig._consider_importhookc                 C   sF   || j _tjdrdS dd t D }t|D ]}|| q2dS )zGiven an importhook, mark for rewrite any top-level
        modules or packages in the distribution package for
        all pytest plugins.PYTEST_DISABLE_PLUGIN_AUTOLOADNc                 s   s:   | ]2}t d d |jD r|jp"g D ]}t|V  q$qdS )c                 s   s   | ]}|j d kV  qdS )r7  N)group)r   epr?   r?   r@   	<genexpr>  r   z=Config._mark_plugins_for_rewrite.<locals>.<genexpr>.<genexpr>N)r  entry_pointsfilesrP   )r   distfiler?   r?   r@   r    s   z3Config._mark_plugins_for_rewrite.<locals>.<genexpr>)	r   r   rU   r   r   r#   distributionsrN  r;  )rH   rj   rG  r   r?   r?   r@   r    s    z Config._mark_plugins_for_rewrite)rX   viarD   c                 C   s8   || j _z"| j j|t| jd W | j `n| j `0 |S )zValidate known args.r  )rj  Z_config_source_hintr  r  rh  )rH   rX   r  r?   r?   r@   _validate_args  s    zConfig._validate_args)rX   r  r  r  r  r   rD   c                C   s   |rt jj}|}n~||krvt jj}|r,|}qzg }|D ]}	|ttj|	dd q4|rz|sz|rzd}
| jt	|
dd ng }|st jj
}t|g}||fS )zDecide the args (initial paths/nodeids) to use given the relevant inputs.

        :param warn: Whether can issue warnings.
        T)	recursivezNo files were found in testpaths; consider removing or adjusting your testpaths configuration. Searching recursively from the current directory instead.r5   
stacklevel)r   r^  r[  r]  extendsortedr  iglobissue_config_time_warningr-   r\  rP   )rH   rX   r  r  r  r  r   sourceresultrB   warning_textr?   r?   r@   r    s,    
zConfig._decide_args)rX   r  rD   c              
   C   s  |r8t jdd}t|r8| t|d| |d d < | | |rd| | dd| |d d < | j	j
|t| jd| _|   | | | jj|dd t jd	s| jd
 | j  | j	j
|t| jd| _|   |   | jjr| jtjjdd | jjd u rB| jd ur0t| jj}n
t| j}|| j_z| j j!| || j	d W nX t"y } z>| jj#s| jj$r| jt%d|j& dd n W Y d }~n
d }~0 0 d S )NZPYTEST_ADDOPTSr8  zvia PYTEST_ADDOPTSr  zvia addopts configr  Fr   r  r7  r4   r  )r  rX   rc  z"could not load initial conftests: )'rU   r   r   r)  r  shlexrT   r  r  rj  parse_known_argsr  rh  r  _checkversionr  r   r   r<  r4  _validate_plugins_warn_about_skipped_pluginsstrictr  r   r   ZSTRICT_OPTIONr  rv  rP   r   r  rj   r  rA   r  r  r-   rB   )rH   rX   r  Zenv_addoptsr  rm   r?   r?   r@   	_preparse  sZ    







zConfig._preparse)r   )NNNc                 c   s   d V  |    d S rE   )_validate_config_optionsrM   r?   r?   r@   pytest_collection=  s    zConfig.pytest_collectionc                 C   sn   dd l }| jdd }|rjddlm} t|ts@|d| j ||||j	krj|d| j||j	f d S )Nr   r  Versionz'%s: 'minversion' must be a single valuez6%s: 'minversion' requires pytest-%s, actual pytest-%s')
r2   r  r   packaging.versionr  r   rP   r   rv  __version__)rH   r2   Zminverr  r?   r?   r@   r  D  s"    
zConfig._checkversionc                 C   s(   t |  D ]}| d| d qd S )NzUnknown config option: r`   )r  _get_unknown_ini_keys_warn_or_fail_if_strict)rH   keyr?   r?   r@   r  [  s    zConfig._validate_config_optionsc           
   	   C   s   t | d}|sd S ddlm} ddlm}m} | j }dd |D }g }|D ]l}z||}	W n  |y   |	| Y qRY n0 |	j
|vr|	| qR|	jj|||	j
 ddsR|	| qR|rtd	d
|d S )Nr  r   r  )InvalidRequirementRequirementc                 S   s   i | ]\}}|j |jqS r?   )project_namer  )r   r   r  r?   r?   r@   
<dictcomp>i  r   z,Config._validate_plugins.<locals>.<dictcomp>T)prereleaseszMissing required plugins: {}r   )r  r  r  r  Zpackaging.requirementsr  r  r   Zlist_plugin_distinfor   r   	specifiercontainsr   rL   r   )
rH   r  r  r  r  Zplugin_infoZplugin_dist_infoZmissing_pluginsZrequired_pluginreqr?   r?   r@   r  _  s0    



zConfig._validate_plugins)r   rD   c                 C   s&   | j jrt|| jt|dd d S )Nr5   r  )r  Zstrict_configr   r  r-   )rH   r   r?   r?   r@   r    s    zConfig._warn_or_fail_if_strictc                    s   | j j  fdd| jD S )Nc                    s   g | ]}| vr|qS r?   r?   )r   r   Zparser_inicfgr?   r@   
<listcomp>  r   z0Config._get_unknown_ini_keys.<locals>.<listcomp>)rj  _inidictr  rM   r?   r  r@   r    s    zConfig._get_unknown_ini_keysc                 C   s   | j g ksJ d| jjjt| jdd | j||d | jj| |d d| j_	zH| jj
|| j| jd}| j|| jj| d| jj| jdd	\| _ | _W n ty   Y n0 d S )
Nz:can only parse cmdline args at most once per Config object)r   r   r  )r_   rX   Tr  r  r  )rX   rj   Zpytest_addhooksr   r   r   r  Zpytest_cmdline_preparserj  Zafter_preparseZparse_setoptionrh  r  r  r  r  r   r   r  rr  r   )rH   rX   r  r?   r?   r@   r    s0    

zConfig.parse)warningr  rD   c                 C   s   | j drdS | jjpg }| d}tjdd8}tdt| t	|| tj
||d W d   n1 sp0    Y  |rt|d }|jj|j|jjf}| jjjt|d	 d
d|dd dS )a   Issue and handle a warning during the "configure" stage.

        During ``pytest_configure`` we can't capture warnings using the ``catch_warnings_for_item``
        function because it is not possible to have hookwrappers around ``pytest_configure``.

        This function is mainly intended for plugins that need to issue warnings during
        ``pytest_configure`` (or similar stages).

        :param warning: The warning instance.
        :param stacklevel: stacklevel forwarded to warnings.warn.
        r   NfilterwarningsT)recordalwaysr  r   r   r_   r8  )Zwarning_messagewhenr  locationr   )r   r9  r  Zpythonwarningsr  r   rz  r{  r   apply_warning_filtersr   rb   	_getframef_codeco_filenamef_linenoco_namerj   Zpytest_warning_recordedr   r   )rH   r  r  cmdline_filtersconfig_filtersrecordsframer  r?   r?   r@   r    s&    

,z Config.issue_config_time_warning)r   rd   rD   c                 C   s&   |  |}t|tsJ || dS )zAdd a line to an ini-file option. The option must have been
        declared but might not yet be set in which case the line becomes
        the first line in its value.N)r  r   r   r   )rH   r   rd   r  r?   r?   r@   r     s    
zConfig.addinivalue_liner   c                 C   s<   z| j | W S  ty6   | | | j |< }| Y S 0 dS )a  Return configuration value from an :ref:`ini file <configfiles>`.

        If the specified name hasn't been registered through a prior
        :func:`parser.addini <pytest.Parser.addini>` call (usually from a
        plugin), a ValueError is raised.
        N)rn  r  _getini)rH   r   valr?   r?   r@   r    s
    zConfig.getini)r   r   valuec                 C   s   d| }t ||d S )Nzunknown configuration type: )rl   )rH   r   r   r  rq   r?   r?   r@   _getini_unknown_type  s    
zConfig._getini_unknown_typec           	   
      s  z| j j| \}}}W n4 tyJ } ztd||W Y d }~n
d }~0 0 | |}|d u rz| j| }W q ty   |d ur| Y S |d u rY dS g  Y S 0 n|}|dkr| jd usJ | jj t|t	rt
|n|} fdd|D S |dkrt|t	rt
|S |S |dkrNt|t	rHdd td	d
 |dD S |S nD|dkrhtt	| S |dkrv|S |d u r|S | |||S d S )Nzunknown configuration value: r8  pathsc                    s   g | ]} | qS r?   r?   )r   r  Zdpr?   r@   r    r   z"Config._getini.<locals>.<listcomp>rX   Zlinelistc                 S   s   g | ]}|r|qS r?   r?   )r   tr?   r?   r@   r    r   c                 S   s   |   S rE   r+  )r  r?   r?   r@   <lambda>  r   z Config._getini.<locals>.<lambda>r`   r   string)rj  r  r  rl   _get_override_ini_valuer  rv  r   r   rP   r  rT   map
_strtoboolr+  r  )	rH   r   descriptionr   ry  rm   Zoverride_valuer  Zinput_valuesr?   r  r@   r    sB    &





zConfig._getini)r   rB   r  rD   c           	      C   s   z | j ||| d|\}}W n ty4   Y d S 0 |jd usDJ t|jj}g }|D ]>}t|tj	rrt|}n|
dtj}t|| }|| qX|S )Nr  rH  )r   r  	getoptionr  r2  r   r   r   rU   r   r   rV   r&   r   )	rH   r   rB   r  r  ZrelrootsmodpathvaluesZrelrootr?   r?   r@   _getconftest_pathlist  s     
zConfig._getconftest_pathlistr   c                 C   sj   d }| j D ]Z}z|dd\}}W n4 tyV } ztd||W Y d }~q
d }~0 0 ||kr
|}q
|S )Nr   r   z9-o/--override-ini expects option=value style (got: {!r}).)ro  rT   rl   r   rL   )rH   r   r  Z
ini_configr  Zuser_ini_valuerm   r?   r?   r@   r  -  s    
zConfig._get_override_ini_valueF)r   skipc              
   C   s   | j ||}z&t| j|}|du r0|r0t||W S  ty } zR|tur\|W  Y d}~S |rzddl}|d|d td||W Y d}~n
d}~0 0 dS )ai  Return command line option value.

        :param name: Name of the option.  You may also specify
            the literal ``--OPT`` option instead of the "dest" option name.
        :param default: Default value if no option of that name exists.
        :param skip: If True, raise pytest.skip if option does not exists
            or has a None value.
        Nr   zno z option foundzno option named )	rp  r   r   rh  r   notsetr2   r  rl   )rH   r   ry  r  r  rm   r2   r?   r?   r@   r  @  s    	zConfig.getoptionc                 C   s
   |  |S )z$Deprecated, use getoption() instead.r  rH   r   rB   r?   r?   r@   getvalueX  s    zConfig.getvaluec                 C   s   | j |ddS )z-Deprecated, use getoption(skip=True) instead.T)r  r  r  r?   r?   r@   getvalueorskip\  s    zConfig.getvalueorskip)r   rD   c                 C   s.   t  s*|dkrd}nd}| jt|dd d S )Nr  zRASSERTIONS ARE NOT EXECUTED and FAILING TESTS WILL PASS.  Are you using python -O?zassertions not in test modules or plugins will be ignored because assert statements are not executed by the underlying Python interpreter (are you using python -O?)
r5   r  )_assertion_supportedr  r-   )rH   r   r  r?   r?   r@   r  `  s    z$Config._warn_about_missing_assertionc                 C   s4   | j jD ]&\}}| jtd|d| dd qd S )Nzskipped plugin : r4   r  )r   r   r  r-   )rH   rQ  rq   r?   r?   r@   r  u  s
    z"Config._warn_about_skipped_plugins)N)T)T)N)N)Gr8   r9   r:   r;   r"   dataclasses	dataclassr   rY  Enumr^  r   r   rG   propertyr   r  rv  r   rx  r|  rk   r!   r  r   rP   r   r   r   rf  rg  r  r  classmethodr  ri  hookimplr  r   r  r  r  r  r   r   r  r  r   r  r  r  r  r  r  r  Warningintr  r   r  r   r  r  r  r  r  r  r	  r
  r  r  r?   r?   r?   r@   r     s   

!C			 	+; #7
c                   C   s*   zds
J W n t y    Y dS 0 dS d S )NFT)AssertionErrorr?   r?   r?   r@   r  }  s
    r  )r_   r  rD   c                 C   sZ   t |d}| jjdkrd|_n| jjdkr0d|_| jjdkrDd|_n| jjdkrVd|_|S )zCreate a TerminalWriter instance configured according to the options
    in the config object.

    Every code which requires a TerminalWriter object and has access to a
    config object should use this function.
    )r  yesTnoF)r!   rh  colorZ	hasmarkupZcode_highlight)r_   r  ro   r?   r?   r@   create_terminal_writer  s    	
r  )r  rD   c                 C   s2   |   } | dv rdS | dv r dS td| dS )a  Convert a string representation of truth to True or False.

    True values are 'y', 'yes', 't', 'true', 'on', and '1'; false values
    are 'n', 'no', 'f', 'false', 'off', and '0'.  Raises ValueError if
    'val' is anything else.

    .. note:: Copied from distutils.util.
    )yr  r  trueon1T)r,  r  ffalseoff0Fzinvalid truth value N)lowerrl   )r  r?   r?   r@   r    s    	r  2   )maxsizezwarnings._ActionKind)r.  escaperD   c             
   C   s  d}t d|  d}| d}t|dkrXd}t dt| d| d	}t|j|d
t|dk rp|d qXdd |D \}}}	}
}zt|}W n: tjy } z t|jt	|d
W Y d}~n
d}~0 0 zt
|	}W n8 ty   t }|jdd}t|j|d
Y n0 |r.|r.t|}|
rH|rHt|
d }
|rzt|}|dk rjtdW nB ty } z(t|jd|d| d
W Y d}~n
d}~0 0 nd}||||
|fS )zParse a warnings filter string.

    This is copied from warnings._setoption with the following changes:

    * Does not apply the filter.
    * Escaping is optional.
    * Raises UsageError so we get nice error messages on failure.
    TzF        while parsing the following warning configuration:

          z8

        This error occurred:

        {error}
        :r7   zJhttps://docs.python.org/3/library/warnings.html#describing-warning-filtersz            Too many fields (z), expected at most 5 separated by colons:

              action:message:category:module:line

            For more information please consult: z
            )errorr8  c                 s   s   | ]}|  V  qd S rE   r  )r   sr?   r?   r@   r    r   z'parse_warning_filter.<locals>.<genexpr>Nr  )r\   z\Zr   znumber is negativezinvalid lineno r  )r   rT   r)  r   rL   r   r   
_getaction_OptionErrorrP   _resolve_warning_categoryrO   r   Zfrom_currentrg   rer%  r  rl   )r.  r%  __tracebackhide__Zerror_templaterS  Zdoc_urlr'  Zaction_r   Z	category_moduleZlineno_actionrm   categoryrn   Zexception_textlinenor?   r?   r@   parse_warning_filter  s\    
	*

r2  )r0  rD   c                 C   sr   d}| st S d| vr"ddl}| }n | d\}}}t|dd|g}t||}t|t sdt| dttt  |S )z
    Copied from warnings._getcategory, but changed so it lets exceptions (specially ImportErrors)
    propagate so we can get access to their tracebacks (#9218).
    T.r   Nz is not a Warning subclass)	r  builtins
rpartitionr=  r   
issubclassr   r	   r   )r0  r-  r   klassr.  r   catr?   r?   r@   r+    s    

r+  )r  r  rD   c                 C   s<   | D ]}t jt|dd  q|D ]}t jt|dd  q dS )z8Applies pytest-configured filters to the warnings moduleF)r%  TN)r   r  r2  )r  r  r.  r?   r?   r@   r    s    r  )NN)NN)NN)N)r;   rf  collections.abcrC  r  r  rY  r  r   rU   r,  r  rb   r   r   	functoolsr   pathlibr   textwrapr   r   r   typingr   r   r	   r
   r   r   r   r   r   r   r   r   r   r   r   r   r   Zpluggyr   r   r   Z_pytest._coder   Z_pytest.deprecatedZ_pytest.hookspec
exceptionsr   r   Z	findpathsr   r   r    Z_pytest._ior!   Z_pytest.compatr"   r#   Z_pytest.outcomesr$   r%   Z_pytest.pathlibr&   r'   r(   r)   r*   r+   Z_pytest.stashr,   Z_pytest.warning_typesr-   r.   Z_pytest._code.coder/   Z_pytest.terminalr0   re  r1   rU  r@  r  r   IntEnumr3   rO   rA   _codeZTracebackEntryr   rW   rP   r  rr   r|   r}   r   r   r0  version_infor   r   r:  r   r   r   ra   r   r   r   r   r5  r  rE  r  rN  r   r  r  r  r  r2  r+  r  r?   r?   r?   r@   <module>   s\  
  
2

  
   	

    !A      
 G