o
    iJ9                     @   s
  d 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
 ejejjddG dd de	jZG dd dejZG dd deZG dd deeZdd ZG dd deZdS )zDynamic collection API.

Dynamic collections act like Query() objects for read operations and support
basic add/delete mutation.

   )
attributes)exc)
interfaces)object_mapper)object_session)
properties)
strategies)util)Query   )logdynamic)lazyc                   @   s   e Zd Zdd ZdS )
DynaLoaderc              	   C   sj   d| _ | jstd| j | jjtjtjfvr t	
d| j  tj| j|dt| jj| jj| jjd d S )NTztOn relationship %s, 'dynamic' loaders cannot be used with many-to-one/one-to-one relationships and/or uselist=False.zOn relationship %s, 'dynamic' loaders cannot be used with many-to-one/one-to-one relationships and/or uselist=False.  This warning will be an exception in a future release.)	useobject
impl_classtarget_mapperorder_byquery_class)is_class_leveluselistr   InvalidRequestErrorparent_property	directionr   	ONETOMANY
MANYTOMANYr	   warnr   _register_attributeDynamicAttributeImplmapperr   r   )selfr    r!   Q/var/www/edux/Edux_v2/venv/lib/python3.10/site-packages/sqlalchemy/orm/dynamic.pyinit_class_attribute    s2   
zDynaLoader.init_class_attributeN)__name__
__module____qualname__r#   r!   r!   r!   r"   r      s    r   c                       s  e Zd ZdZdZdZdZdZ	d& fdd	Ze	j
fddZde	jfdd	Zejd
d Zejdd Z	d&ddZ	d&ddZdd Zde	j
dddfddZdd Zdd Ze	j
fddZe	jfddZe	j
fddZe	j
fd d!Ze	j
fd"d#Ze	j
fd$d%Z  ZS )'r   TFNc           	         s\   t t| j||||fi | || _|| _|st| _d S t| v r'|| _d S t	|| _d S N)
superr   __init__r   r   AppenderQueryr   AppenderMixinmromixin_user_query)	r    class_keytypecallabledispatchr   r   r   kw	__class__r!   r"   r)   E   s   


zDynamicAttributeImpl.__init__c                 C   s&   |t j@ s| |t jjS | | |S r'   )r   SQL_OK_get_collection_historyPASSIVE_NO_INITIALIZEadded_itemsr   )r    statedict_passiver!   r!   r"   get\   s   
zDynamicAttributeImpl.getc                 C   s*   |t j@ s| ||jS | ||}|jS r'   )r   r5   r6   r8   added_plus_unchanged)r    r9   r:   	user_datar;   historyr!   r!   r"   get_collectiond   s   
z#DynamicAttributeImpl.get_collectionc                 C      t | t jS r'   )r   Event	OP_APPENDr    r!   r!   r"   _append_tokenq      z"DynamicAttributeImpl._append_tokenc                 C   rA   r'   )r   rB   	OP_REMOVErD   r!   r!   r"   _remove_tokenu   rF   z"DynamicAttributeImpl._remove_tokenc                 C   sl   |d u r
|  ||}|| | jjD ]}||||p| j}q| jr2|d ur4| t||d d S d S d S NT)	_modified_event	add_addedr1   appendrE   trackparentsethasparentr   instance_stater    r9   r:   value	initiatorcollection_historyfnr!   r!   r"   fire_append_eventy   s   
z&DynamicAttributeImpl.fire_append_eventc                 C   sd   |d u r
|  ||}|| | jr |d ur | t||d | jjD ]}||||p-| j q$d S )NF)	rJ   add_removedrM   rN   r   rO   r1   removerH   rP   r!   r!   r"   fire_remove_event   s   
z&DynamicAttributeImpl.fire_remove_eventc                 C   sD   | j |jvrt| ||j| j < ||| tj d|| j < |j| j  S rI   )r/   committed_stateCollectionHistoryrJ   r   	NEVER_SET)r    r9   r:   r!   r!   r"   rJ      s
   
z$DynamicAttributeImpl._modified_eventc	                 C   s   |r
|j | j u r
d S |r|d u rd S |}	t|	}
|jr$t| ||}| ||}|js1|j}n||j}tj}|	|
}||

|}|
|}|
D ]}||v r]| j|||d |d qM|D ]}| j|||d |d q`d S )N)rS   )parent_tokenlisthas_identityr	   IdentitySetr<   rJ   r8   unionintersection
differencerU   rX   )r    r9   r:   rQ   rR   r;   	check_oldpop_adaptiterable
new_valuesold_collectionrS   idset	constants	additionsremovalsmemberr!   r!   r"   set   sJ   

zDynamicAttributeImpl.setc                 O   s   t  r'   NotImplementedError)r    argskwargsr!   r!   r"   delete   s   zDynamicAttributeImpl.deletec                 C   s   t d)Nz7Dynamic attributes don't support collection population.ro   )r    r9   r:   rQ   r!   r!   r"   set_committed_value   s   z(DynamicAttributeImpl.set_committed_valuec                 C   s   |  ||}| S r'   )r6   
as_historyr    r9   r:   r;   cr!   r!   r"   get_history   s   z DynamicAttributeImpl.get_historyc                 C   s   |  ||}dd |jD S )Nc                 S   s   g | ]	}t ||fqS r!   )r   rO   ).0xr!   r!   r"   
<listcomp>   s    z8DynamicAttributeImpl.get_all_pending.<locals>.<listcomp>)r6   	all_itemsrv   r!   r!   r"   get_all_pending   s   z$DynamicAttributeImpl.get_all_pendingc                 C   sF   | j |jv r|j| j  }nt| |}|jr!|tj@ r!t| ||dS |S )N)apply_to)r/   rY   rZ   r^   r   INIT_OK)r    r9   r;   rw   r!   r!   r"   r6      s   
z,DynamicAttributeImpl._get_collection_historyc                 C       || ur|  |||| d S d S r'   )rU   r    r9   r:   rQ   rR   r;   r!   r!   r"   rL         zDynamicAttributeImpl.appendc                 C   r   r'   )rX   r   r!   r!   r"   rW      r   zDynamicAttributeImpl.removec                 C   s   | j |||||d d S )N)r;   )rW   r   r!   r!   r"   rd      s   zDynamicAttributeImpl.popr'   )r$   r%   r&   uses_objectsdefault_accepts_scalar_loadersupports_population
collectionr   r)   r   PASSIVE_OFFr<   r7   r@   r	   memoized_propertyrE   rH   rU   rX   rJ   rn   rs   rt   rx   r}   r6   rL   rW   rd   __classcell__r!   r!   r3   r"   r   >   sN    






6


r   c                       sp   e Zd ZdZ fddZdd Zeedd Zdd	 Zd
d Zdd Z	dddZ
dd Zdd Zdd Z  ZS )r+   Nc                    s   t t| |jd  |  | _}|| _t|}|j| jj	 }|j
d ur,|jj|j
f| _|j|dd| _| jjr?| jj| _d S d S )NF)alias_secondary)r(   r+   r)   r   objinstanceattrr   _propsr/   	secondaryr   
selectable	_from_obj_with_parent
_criterionr   	_order_by)r    r   r9   r   r   propr3   r!   r"   r)   	  s   
zAppenderMixin.__init__c                 C   sD   t | j}|d ur| jr|jr| j|v r|  t| js d S |S r'   )r   r   	autoflushflushorm_utilr^   r    sessr!   r!   r"   session  s   

zAppenderMixin.sessionc                 C   s   d S r'   r!   )srz   r!   r!   r"   <lambda>-  s    zAppenderMixin.<lambda>c                 C   s:   | j }|d u rt| jt| jtjjS t| 	|S r'   )
r   iterr   r6   r   rO   r   r7   r8   _cloner   r!   r!   r"   __iter__/     
zAppenderMixin.__iter__c                 C   s<   | j }|d u r| jt| jtj|S | |	|S r'   )
r   r   r6   r   rO   r   r7   indexedr   __getitem__)r    indexr   r!   r!   r"   r   ;  s   
zAppenderMixin.__getitem__c                 C   s:   | j }|d u rt| jt| jtjjS | 	|
 S r'   )r   lenr   r6   r   rO   r   r7   r8   r   countr   r!   r!   r"   r   E  r   zAppenderMixin.countc                 C   s~   | j }|d u rt|}|d u rtdt|| jjf | jr*| j| jj	|d}n|
| jj	}| j|_| j|_| j|_|S )NzParent instance %s is not bound to a Session, and no contextual session is established; lazy load operation of attribute '%s' cannot proceed)r   )r   r   orm_excDetachedInstanceErrorr   instance_strr   r/   r   r   queryr   r   r   )r    r   r   r   r!   r!   r"   r   Q  s    zAppenderMixin._clonec                 C   s0   |D ]}| j t| jt| j|d  qd S r'   r   rL   r   rO   r   instance_dict)r    iteratoritemr!   r!   r"   extendk  s   

zAppenderMixin.extendc                 C   &   | j t| jt| j|d  d S r'   r   r    r   r!   r!   r"   rL   t     

zAppenderMixin.appendc                 C   r   r'   )r   rW   r   rO   r   r   r   r!   r!   r"   rW   |  r   zAppenderMixin.remover'   )r$   r%   r&   r   r)   r   propertyr   r   r   r   r   rL   rW   r   r!   r!   r3   r"   r+     s    

	r+   c                   @   s   e Zd ZdZdS )r*   zBA dynamic query that supports basic collection storage operations.N)r$   r%   r&   __doc__r!   r!   r!   r"   r*     s    r*   c                 C   s   d| j  }t|t| fd| iS )zAReturn a new class with AppenderQuery functionality layered over.Appenderr   )r$   typer+   )clsnamer!   r!   r"   r-     s   
r-   c                   @   sR   e Zd ZdZdddZedd Zedd Zd	d
 Zdd Z	dd Z
dd ZdS )rZ   zDOverrides AttributeHistory to receive append/remove events directly.Nc                 C   sb   |rt ||d}t|| _|j| _|j| _d| _d S t | _t | _t | _d| _d S )NFT)r*   r   r	   OrderedIdentitySetunchanged_itemsr8   deleted_items_reconcile_collection)r    r   r9   r~   collr!   r!   r"   r)     s   




zCollectionHistory.__init__c                 C   s   t | j| jS r'   )r]   r8   r`   r   rD   r!   r!   r"   r=     s   z&CollectionHistory.added_plus_unchangedc                 C   s   t | j| j| jS r'   )r]   r8   r`   r   r   rD   r!   r!   r"   r|     s
   zCollectionHistory.all_itemsc                 C   s`   | j r| j| j}| j| j}| j|}n| j| j| j}}}tt|t|t|S r'   )	r   r8   rb   r   r   ra   r   Historyr]   )r    addeddeleted	unchangedr!   r!   r"   ru     s   
zCollectionHistory.as_historyc                 C   s   t | j| S r'   )r]   r8   )r    r   r!   r!   r"   r     s   zCollectionHistory.indexedc                 C   s   | j | d S r'   )r8   addr    rQ   r!   r!   r"   rK     s   zCollectionHistory.add_addedc                 C   s*   || j v r| j | d S | j| d S r'   )r8   rW   r   r   r   r!   r!   r"   rV     s   
zCollectionHistory.add_removedr'   )r$   r%   r&   r   r)   r   r=   r|   ru   r   rK   rV   r!   r!   r!   r"   rZ     s    


rZ   N)r    r   r   r   r   r   r   r   r   r	   r   r   r
   r   class_loggerRelationshipPropertystrategy_forAbstractRelationshipLoaderr   AttributeImplr   objectr+   r*   r-   rZ   r!   r!   r!   r"   <module>   s,    I