K i>dZddlmZddlZddlZddlZddlZddlZddlm Z m Z m Z ddl m Z ddlmZddlmZmZddlmZdd lmZdd lmZmZdd lmZmZmZmZd d lmZd dl m!Z!m"Z#d dl$m%Z%d dl&m'Z'ddl(m)Z)er ddl*m+Z+ddl,m-Z-edZ.eddZ/GddZ0 d0 d1dZ1 d0 d2dZ2d3dZ3d4dZ4d5dZ5 d6 d7dZ6d8d Z7d9d!Z8 d:d"Z9 d6 d;d#Z: d6 dd'Z=d?d(Z>d@d)Z? d0 dAd*Z@ dB dCd+ZAGd,d-ZBGd.d/e e.e/fZCy)DaiUtility functions to expand configuration directives or special values (such glob patterns). We can split the process of interpreting configuration files into 2 steps: 1. The parsing the file contents from strings to value objects that can be understand by Python (for example a string with a comma separated list of keywords into an actual Python list of strings). 2. The expansion (or post-processing) of these values according to the semantics ``setuptools`` assign to them (for example a configuration field with the ``file:`` directive should be expanded from a list of file paths to a single string with the contents of those files concatenated) This module focus on the second step, and therefore allow sharing the expansion functions among several configuration file formats. **PRIVATE MODULE**: API reserved for setuptools internal usage only. ) annotationsN)IterableIteratorMapping) ConfigParser)iglob) ModuleSpec all_suffixes)chain)Path) ModuleType TracebackType) TYPE_CHECKINGAnyCallableTypeVar)_static)StrPath same_path)find_package_path)SetuptoolsWarning)DistutilsOptionError)Self) Distribution_K_V_coT) covariantc(eZdZdZddZddZddZy) StaticModulez>Proxy to a module object that avoids executing arbitrary code.ctjtj|jj }t |jt|` yN) astparsepathlibr origin read_bytesvarsupdatelocalsself)r+namespecmodules ^/mnt/ssd/data/python-lab/Trading/venv/lib/python3.12/site-packages/setuptools/config/expand.py__init__zStaticModule.__init__8s?7<< 4??AB T &(# Ic#<K|jjD]|ttjrfdj DEd{;ttj sVjscjjf~y7Jw)Nc3:K|]}|jfywr")value).0target statements r/ z1StaticModule._find_assignments..@sV&VY__5Vs) r.body isinstancer#Assigntargets AnnAssignr4r6)r+r7s @r/_find_assignmentszStaticModule._find_assignments=sn)) :I)SZZ0VIDUDUVVVIs}}5)// ''99  :VsA BBB0 B=Bc tfd|jDS#t$r }t|jd|d}~wwxYw)zHAttempt to load an attribute "statically", via :func:`ast.literal_eval`.c3K|]E\}}t|tjr&|jk(rtj|Gywr")r:r#Nameid literal_eval)r5r6r4attrs r/r8z+StaticModule.__getattr__..GsA!FEfchh/FII4E  'sA Az has no attribute N)nextr> ExceptionAttributeErrorr,)r+rDes ` r/ __getattr__zStaticModule.__getattr__Ds] P%)%;%;%=   P DII;.@!GHa O Ps!% AA  AN)r,strr-r returnNone)rKz!Iterator[tuple[ast.AST, ast.AST]])rDrJ)__name__ __module__ __qualname____doc__r0r>rIr1r/r r 5sH : Pr1r c hd}g}xstj|D]tfd|Drltjj tjj }|j tfdt|dDtjjjtjd}|j||S)aExpand the list of glob patterns, but preserving relative paths. :param list[str] patterns: List of glob patterns :param str root_dir: Path to which globs should be relative (current directory by default) :rtype: list >*?[]{}c3&K|]}|v ywr"rQ)r5charr4s r/r8z glob_relative.._s9tu}9sc3K|]B}tjj|jtjdDyw)/N)ospathrelpathreplacesepr5r^root_dirs r/r8z glob_relative..cs9GGOOD(3;;BFFCHsAA T) recursiver\) r]getcwdanyr^abspathjoinextendsortedrr_r`raappend)patternsrcglob_charactersexpanded_values glob_pathr^r4s ` @r/ glob_relativerpPs5OO&299;H) 99 9 Xu(EFI  " " %i4 @ 77??5(3;;BFFCHD  " "4 ()" r1cddlm}tjj xstj fd||D}dj fdt|DS)zReturn the content of the files concatenated using `` `` as str This function is sandboxed and won't reach anything outside ``root_dir`` (By default ``root_dir`` is the current directory). r)always_iterablec3^K|]$}tjj|&ywr"r]r^rhrbs r/r8zread_files..}s V4"'',,x.Vs*- c3LK|]}t|r t|ywr") _assert_local _read_filerbs r/r8zread_files..~s(  x ( 4s!$)more_itertoolsrrr]r^rgrerh_filter_existing_files) filepathsrcrr _filepathss ` r/ read_filesr}qsW/wwx6299;7HV?9;UVJ 99*:6 r1c#K|D]?}tjj|r|'tjd|dAyw)NzFile z cannot be found)r]r^isfileremit)r{r^s r/rzrzsDE 77>>$ J  " "U4(2B#C D EsAAcht|d5}|jcdddS#1swYyxYw)Nzutf-8)encoding)openread)filepathfs r/rxrxs, h )Qvvxs(1cttjj|ttjj|jvrd|d|d}t |y)NzCannot access z (or anything outside )T)r r]r^rgparentsr)rrcmsgs r/rwrwsW BGGOOH %&d277??83L.M.U.UUxl*@ AN"3'' r1c|xstj}|jjd}|j }dj |}|xsd}t |||}t||} tt|||}tj|S#t$rt||} t| |cYSwxYw)aReads the value of an attribute from a module. This function will try to read the attributed statically first (via :func:`ast.literal_eval`), and only evaluate the module if it fails. Examples: read_attr("package.attr") read_attr("package.module.attr") :param str attr_desc: Dot-separated string describing how to reach the attribute (see examples above) :param dict[str, str] package_dir: Mapping of package names to their location in disk (represented by paths relative to ``root_dir``). :param str root_dir: Path to directory containing all the packages in ``package_dir`` (current directory by default). :rtype: str .r0)r]restripsplitpoprh _find_module _find_specgetattrr rattempt_conversionrF _load_spec) attr_desc package_dirrc attrs_path attr_name module_namer^r-r4r.s r/ read_attrrs,&299;H"((-J I((:&K+K  [( ;D k4 (D* [$7C))%00 *D+.vy))*s9*B$$!CCctjj||}|xstjj|}| t ||Sr") importlibutilspec_from_file_location find_specModuleNotFoundError)r module_pathr-s r/rrsF >> 1 1+{ KD  89>>++K8D |!+.. Kr1c t|d|}|tjvrtj|Stjj |}|tj|<|j J|j j||S)NrM)rsysmodulesrrmodule_from_specloader exec_module)r-rr,r.s r/rrst 4[ 1D s{{{{4  ^^ , ,T 2FCKK ;; "" "KKF# Mr1ct||xsi|tjfdtD}t d|DdS)aFind the path to the module named ``module_name``, considering the ``package_dir`` in the build configuration and ``root_dir``. >>> tmp = getfixture('tmpdir') >>> _ = tmp.ensure("a/b/c.py") >>> _ = tmp.ensure("a/b/d/__init__.py") >>> r = lambda x: x.replace(str(tmp), "tmp").replace(os.sep, "/") >>> r(_find_module("a.b.c", None, tmp)) 'tmp/a/b/c.py' >>> r(_find_module("f.g.h", {"": "1", "f": "2", "f.g": "3", "f.g.h": "a/b/d"}, tmp)) 'tmp/a/b/d/__init__.py' c3pK|]-}|tjjd|f/yw)r0Nrt)r5ext path_starts r/r8z_find_module..s=%  <u rww||J(3%8HIJ%s36c3`K|]&}tjj|s#|(ywr")r]r^r)r5xs r/r8z_find_module..s%J  R41aA}Q X6 6 RR Rs0) namespacesfill_package_dirrcc P ddlm}m}ddlm}|sddlm}nddlm}|xstj}|jddg}g} |in|}t||| t dk(r+t fd d|fDr|jd d D]} t|| } |j| fi|} | j!| | s6|j#d | k(rKtj$j'| |rl|j)|| | | S) aWorks similarly to :func:`setuptools.find_packages`, but with all arguments given as keyword arguments. Moreover, ``where`` can be given as a list (the results will be simply concatenated). When the additional keyword argument ``namespaces`` is ``True``, it will behave like :func:`setuptools.find_namespace_packages`` (i.e. include implicit namespaces as per :pep:`420`). The ``where`` argument will be considered relative to ``root_dir`` (or the current working directory when ``root_dir`` is not given). If the ``fill_package_dir`` argument is passed, this function will consider it as a similar data structure to the ``package_dir`` configuration parameter add fill-in any missing package location. :rtype: list r)rrunique_everseen)construct_package_dir) PackageFinder)PEP420PackageFinderwhererrc3>K|]}td| yw)rN) _same_path)r5rsearchs r/r8z find_packages..1sVJvay!$< <Vs)ryrrrsetuptools.discoveryrrrr]curdirrlistlenall setdefault _nest_pathfindrigetr^samefiler))rrrckwargsrrrrrrpackagesr^ package_pathpkgsrs @r/ find_packagesr s0@: 6M$299H JJw &EH-5r;K //%"89 :F 6{aCVsHoVV##Bq 2G!(D1 !}!!,9&9    $ ,0@0@x0X  # #$9$$E FG Or1c|dvr|ntjj||}tjj|S)N>rr)r]r^rhnormpath)parentr^s r/rr@s4Y&6BGGLL,FD 77  D !!r1ct|r|n|}t|tr|St|drdj t t|S|S)z`When getting the version directly from an attribute, it should be normalised to string. __iter__r)callabler:rJhasattrrhmap)r4_values r/versionrEsJ!UWUF&# vz"xxC())Xr1c6d|vr|jd|d<|S)NrSr)r) package_datas r/canonic_package_datarRs% l'++C0 R r1c t|tr|S|jDcgc]\}}|t||fc}}Scc}}w)zFor compatibility with ``setup.py``, ``data_files`` should be a list of pairs instead of a dict. This function also expands glob patterns. )r:rrrp) data_filesrcdestrls r/canonic_data_filesrXsO*d#)..0  D( }Xx01  sAc tdd}t|_|j|||j Dcic]\}}|t |j !}}}|j |jd|Scc}}w)a?Given the contents of entry-points file, process it into a 2-level dictionary (``dict[str, dict[str, str]]``). The first level keys are entry-point groups, the second level keys are entry-point names, and the second level values are references to objects (that correspond to the entry-point value). N)=)default_section delimiters)rrJ optionxform read_stringrdictrr)text text_sourceparserrrgroupss r/ entry_pointsrisr$6 BFF t[)-3\\^ >> def obtain_mapping(): ... print("Running expensive function!") ... return {"key": "value", "other key": "other value"} >>> mapping = LazyMappingProxy(obtain_mapping) >>> mapping["key"] Running expensive function! 'value' >>> mapping["other key"] 'other value' c ||_d|_yr")_obtainr)r+obtain_mapping_values r/r0zLazyMappingProxy.__init__s+ 15 r1c\|j|j|_|jSr")rrrs r/_targetzLazyMappingProxy._targets# ;; ,,.DK{{r1c(|j|Sr")r)r+keys r/ __getitem__zLazyMappingProxy.__getitem__s||~c""r1c4t|jSr")rrrs r/__len__zLazyMappingProxy.__len__s4<<>""r1c4t|jSr")iterrrs r/rzLazyMappingProxy.__iter__sDLLN##r1N)rz Callable[[], Mapping[_K, _V_co]]rKrL)rKzMapping[_K, _V_co])rrrKr)rKint)rKz Iterator[_K]) rMrNrOrPr0rrrrrQr1r/r r s  6 ##$r1r r")rlz Iterable[str]rcStrPath | NonerK list[str])r{zStrPath | Iterable[StrPath]rcrrKrJ)r{zIterable[StrPath]rKzIterator[StrPath])rzbytes | StrPathrKrJ)rrrcrJ)NN)rrJrMapping[str, str] | NonercrrKr)rrJrrrKr )r-r rrJrKr )rrJrrrcrrKz str | None)rrJrrrcrrKr)rzdict[str, str]rrrcrrKzdict[str, Callable])rzdict[str, str] | NonercrrKr)rrr^rrKrJ)r4z$Callable | Iterable[str | int] | strrKrJ)rrrKr)rz list | dictrcrrKzlist[tuple[str, list[str]]])z entry-points)rrJrrJrKzdict[str, dict[str, str]])DrP __future__rr#rr]r%rcollections.abcrrr configparserrglobrimportlib.machineryr r itertoolsr r typesr rtypingrrrrrr_pathrrr discoveryrwarningsrdistutils.errorsrtyping_extensionsrsetuptools.distrrrr rpr}rzrxrwrrrrrrrrrrrrrr rQr1r/r-s;(#   77%8+884)(1&, T]4(PP89='5DHL*6D(E -1#%*%*)%*%* %*PDD#;DGNDD2-1# ' ') ' ' '$-1#S S)SS S.2# 4,4 4  4n" 9='5 $#1 $(7(7V$wr5y)$r1