o znh3@sdZddlmZddlZddlmZddlmZddlmZdd lm Z e e Z d d Z d Zd ZGdddeZGdddeZee_GdddeZGdddeZGdddeZGdddeZGdddeeZdS)z@Path tracking utilities, representing mapper graph traversals. )chainN) class_mapper)exc) inspection)utilcCs t|SN) PathRegistry deserializepathrG/usr/local/lib/python3.10/dist-packages/sqlalchemy/orm/path_registry.py_unreduce_path r* _sa_defaultc@seZdZdZdZdZdZddZddZdd Z d/d d Z d dZ e ddZ ddZddZddZddZeddZeddZeddZedd Zd!d"Zed#d$Zed%d&Zed'd(Zd)d*Zd+d,Zd-d.Zd S)0r aRepresent query load paths and registry functions. Basically represents structures like: (, "orders", , "items", ) These structures are generated by things like query options (joinedload(), subqueryload(), etc.) and are used to compose keys stored in the query._attributes dictionary for various options. They are then re-composed at query compile/result row time as the query is formed and as rows are fetched, where they again serve to compose keys to look up options in the context.attributes dictionary, which is copied from query._attributes. The path structure has a limited amount of caching, where each "root" ultimately pulls from a fixed registry associated with the first mapper, that also contains elements for each of its property keys. However paths longer than two elements, which are the exception rather than the rule, are generated on an as-needed basis. rFcCs|duo |j|jkSr r selfotherrrr__eq__>zPathRegistry.__eq__cCs"td|||||||jf<dS)Nzset '%s' on path '%s' to '%s')logdebug natural_pathr attributeskeyvaluerrrsetAszPathRegistry.setcCs&td||||||jf|dS)Nz$setdefault '%s' on path '%s' to '%s')rr setdefaultrrrrrr!EszPathRegistry.setdefaultNcCs||jf}||vr ||S|Sr )rrrrrgetIs zPathRegistry.getcC t|jSr lenr rrrr__len__PrzPathRegistry.__len__cCr#r r$r&rrrlengthS zPathRegistry.lengthccs8|j}tdt|dD] }||||dfVq dS)Nrrr)r ranger%)rr irrrpairsWs zPathRegistry.pairscs@fddtdtjdDD] }|jr||rdSqdS)Ncsg|]}j|qSrr .0r+r&rr ]z0PathRegistry.contains_mapper..rrTF)r*r%r is_mapperisa)rmapper path_mapperrr&rcontains_mapper\s $zPathRegistry.contains_mappercCs||jf|vSr r )rrrrrrcontainsczPathRegistry.containscCst|ffSr )r serializer&rrr __reduce__fr7zPathRegistry.__reduce__csRttddfddtdtdDDfddtdtdDdgS)NcSsg|]}|jqSr)class_)r.mrrrr/msz0PathRegistry._serialize_path..csg|]}|qSrrr-r rrr/msrrcsg|]}|jqSr)rr-r rrr/nr0r)listzipr*r%)clsr rr r_serialize_pathis &"zPathRegistry._serialize_pathcCs6ttdd|D}|r|ddur|dd}|S)NcSs2g|]\}}t||durt|j|ndfqSr )rattrs)r.mclsrrrrr/vsz2PathRegistry._deserialize_path..r)tuplerr>r prrr_deserialize_pathrs zPathRegistry._deserialize_pathcs$fddfdd|DDS)Ncs&g|]\\}}}||f|fqSr)r?r.rr rr>rrr/s z7PathRegistry.serialize_context_dict..cs.g|]\}}t|tr|dvr||fqS)r) isinstancerC)r.kv)tokensrrr/s )items)r>dict_rLr)r>rLrserialize_context_dicts  z#PathRegistry.serialize_context_dictcstfdd|DS)Nc3s.|]\\}}}|t|f|fVqdSr )rCrFrGrHrr s   z8PathRegistry.deserialize_context_dict..)r OrderedDict)r> serializedrrHrdeserialize_context_dictsz%PathRegistry.deserialize_context_dictcCs|j}||Sr )r r?)rr rrrr8s zPathRegistry.serializecCs |durdS||}||Sr )rFcoercerDrrrr s  zPathRegistry.deserializecCs|jr t|j|St|j|Sr )r1CachingEntityRegistryrootSlotsEntityRegistry)r>r3rrr per_mappers  zPathRegistry.per_mappercCstdd||jS)NcS||Sr rprevnextrrrz%PathRegistry.coerce..)rreducerV)r>rawrrrrTszPathRegistry.coercecCs@|dtr t||S|dtrt|j|Std|)N:zinvalid token: %s)endswith_WILDCARD_TOKEN TokenRegistry_DEFAULT_TOKENrVr ArgumentError)rtokenrrrrgs   zPathRegistry.tokencCstdd|j|S)NcSrYr rrZrrrr]r^z&PathRegistry.__add__..)rr_r rrrr__add__rzPathRegistry.__add__cCsd|jj|jfS)Nz%s(%r)) __class____name__r r&rrr__repr__szPathRegistry.__repr__r )rj __module__ __qualname____doc__ __slots__is_tokenis_rootrr r!r"r'propertyr(r,r5r6r9 classmethodr?rFrOrSr8r rXrTrgrhrkrrrrr sD          r c@s,eZdZdZdZZdZdZdZddZ dS) RootRegistryzXRoot registry, defers to mappers so that paths are maintained per-root-mapper. rFTcCs|jSr )_path_registryrentityrrr __getitem__zRootRegistry.__getitem__N) rjrlrmrnr r has_entityis_aliased_classrqrxrrrrrts rtc@s0eZdZdZddZdZdZddZdd Zd S) rdrgparentr rcCs,||_||_|j|f|_|j|f|_dSr r|)rr}rgrrr__init__szTokenRegistry.__init__FTccs|jjs|jjs|jjD] }t|jj||jVqdS|jjr@|jjjr@|V|jjj D] }t|jj||jVq0dS|VdSr ) r}r{rqr3iterate_to_rootrdrgrw_is_with_polymorphic_with_polymorphic_entities)rentrrrgenerate_for_superclassess z'TokenRegistry.generate_for_superclassescCstr )NotImplementedErrorrvrrrrxryzTokenRegistry.__getitem__N) rjrlrmror~rzrprrxrrrrrds rdc@s\eZdZdZddZddZejddZejdd Z e d d Z e d d Z ddZ dS) PropRegistryFcCst|d}|}|jr|jr|j|j}}nH|jrG|jrG|j|jurG|j|jvrG|d|j}|j|}|jrD|j|j}d|_n|}n|jr`|jr`|j|jur`|j |jr`|j|j}||_ ||_|j |f|_ |j |f|_ d|j |j j f|_|j j|_d|j f|_dS)NrBTloader)rinspectr{_use_mapper_pathr}with_polymorphic_mappersr3_entity_for_mapper is_unnaturalr2propr r_wildcard_token_wildcard_path_loader_key_default_path_loader_key _loader_key)rr}rinspnatural_parentsubclass_entityrrrr~sF         zPropRegistry.__init__cCsddd|jDS)Nz -> css|]}t|VqdSr )str)r.elemrrrrP:sz'PropRegistry.__str__..)joinr r&rrr__str__9szPropRegistry.__str__cCs t|jdS)Nr3)hasattrrr&rrrrz<s zPropRegistry.has_entitycCs|jjSr )rr3r&rrrrw@szPropRegistry.entitycCs|jSr rwr&rrrr3DszPropRegistry.mappercCs ||jSr rr&rrr entity_pathHr)zPropRegistry.entity_pathcC"t|ttfr |j|St||Sr )rIintslicer rWrvrrrrxL  zPropRegistry.__getitem__N)rjrlrmrr~rrmemoized_propertyrzrwrrr3rrxrrrrrsI     rc@sHeZdZdZdZddZeddZeddZd d Z e Z d d Z d S)AbstractEntityRegistryrTcCs||_||_|j|_||_|j|f|_|jr>|js|jr>|j|jdjr1|j|jf|_dS|j|jdjf|_dS|j|_dS)NrB) rr}r{rwr rr3r2r)rr}rwrrrr~Xs  zAbstractEntityRegistry.__init__cCs|Sr rr&rrrrxsz"AbstractEntityRegistry.entity_pathcCst|jjSr )rrrwr3r&rrrr3|szAbstractEntityRegistry.mappercCsdS)NTrr&rrr__bool__szAbstractEntityRegistry.__bool__cCrr )rIrrr rrvrrrrxrz"AbstractEntityRegistry.__getitem__N) rjrlrmrorzr~rrrr3r __nonzero__rxrrrrrSs   rc@seZdZdZdS)rW)rr}r{rwr rN)rjrlrmrorrrrrWsrWc@seZdZddZddZdS)rUcCs$t|ttfr |j|St||Sr )rIrrr dictrxrvrrrrxs  z!CachingEntityRegistry.__getitem__cCst||||<}|Sr )r)rritemrrr __missing__sz!CachingEntityRegistry.__missing__N)rjrlrmrxrrrrrrUs rU)rn itertoolsrloggingbaserrrr getLoggerrjrrrcreobjectr rtrVrdrrrWrrUrrrrs(      f9