o
    uvXjp  ã                   @   s”   d Z ddlmZ ddlmZ ddlmZ ddlmZm	Z	m
Z
 ddlmZ g d¢ZG dd	„ d	eƒZG d
d„ deƒZG dd„ deƒZG dd„ deƒZdS )zR
Query subclasses which provide extra functionality beyond simple data retrieval.
é    )Ú
FieldError)Úconnections)ÚQ)ÚCURSORÚGET_ITERATOR_CHUNK_SIZEÚ
NO_RESULTS)ÚQuery)ÚDeleteQueryÚUpdateQueryÚInsertQueryÚAggregateQueryc                   @   s,   e Zd ZdZdZdd„ Zdd„ Zdd„ Zd	S )
r	   zA DELETE SQL query.ÚSQLDeleteCompilerc                 C   s4   || j | i| _ || _|  |¡ t¡}|r|jS dS )Nr   )Ú	alias_mapÚwhereÚget_compilerÚexecute_sqlr   Úrowcount)ÚselfÚtabler   ÚusingÚcursor© r   ú\/var/www/html/myproject/venv/lib/python3.10/site-packages/django/db/models/sql/subqueries.pyÚdo_query   s   zDeleteQuery.do_queryc                 C   sx   d}|   ¡ j}tdt|ƒtƒD ]*}|  ¡ | _|  tdi |j	d |||t … i¤Ž¡ || j
|   ¡ j| j|d�7 }q|S )zº
        Set up and execute delete queries for all the objects in pk_list.

        More than one physical query may be executed if there are a
        lot of values in pk_list.
        r   Ú__in)r   Nr   )Úget_metaÚpkÚrangeÚlenr   Úwhere_classr   Úadd_qr   Úattnamer   Údb_table)r   Úpk_listr   Únum_deletedÚfieldÚoffsetr   r   r   Údelete_batch   s   


ÿzDeleteQuery.delete_batchc                    sÜ   |j ‰ ˆ  ¡  |  ¡  t‡ fdd„ˆ jD ƒƒ}|r |t| jƒkr%ˆ j| _n:|jjj}t| j	j
sCt|jddd�ƒ}|s=dS |  ||¡S ˆ  ¡  | |  ¡ ¡gˆ _ˆ }|  ¡ | _|  t|d�¡ |  |¡ t¡}|rl|jS dS )zÌ
        Delete the queryset in one SQL query (if possible). For simple queries
        this is done by copying the query.query.where to self.query, for
        complex queries by using subquery.
        c                    s   g | ]	}ˆ j | r|‘qS r   )Úalias_refcount)Ú.0Út©Úinnerqr   r   Ú
<listcomp>7   s    z)DeleteQuery.delete_qs.<locals>.<listcomp>r   T)Úflatr   ©Úpk__in)ÚqueryÚget_initial_aliasÚtupler   r   ÚmodelÚ_metar   r   ÚfeaturesÚupdate_can_self_selectÚlistÚvalues_listr'   Úclear_select_clauseÚget_colÚselectr   r    r   r   r   r   r   )r   r1   r   Úinnerq_used_tablesr   Úvaluesr   r   r+   r   Ú	delete_qs,   s(   

ÿ
zDeleteQuery.delete_qsN)Ú__name__Ú
__module__Ú__qualname__Ú__doc__Úcompilerr   r'   r?   r   r   r   r   r	      s    r	   c                       s`   e Zd ZdZdZ‡ fdd„Zdd„ Z‡ fdd„Zd	d
„ Zdd„ Z	dd„ Z
dd„ Zdd„ Z‡  ZS )r
   zAn UPDATE SQL query.ÚSQLUpdateCompilerc                    s   t ƒ j|i |¤Ž |  ¡  d S ©N)ÚsuperÚ__init__Ú_setup_query)r   ÚargsÚkwargs©Ú	__class__r   r   rH   T   s   zUpdateQuery.__init__c                 C   s   g | _ d| _i | _dS )z›
        Run on initialization and at the end of chaining. Any attributes that
        would normally be set in __init__() should go here instead.
        N)r>   Úrelated_idsÚrelated_updates)r   r   r   r   rI   X   s   
zUpdateQuery._setup_queryc                    s   t ƒ  ¡ }| j ¡ |_|S rF   )rG   ÚclonerO   Úcopy)r   ÚobjrL   r   r   rP   a   s   
zUpdateQuery.clonec                 C   sZ   |   |¡ tdt|ƒtƒD ]}|  ¡ | _|  t|||t … d�¡ |  |¡ 	t
¡ qd S )Nr   r/   )Úadd_update_valuesr   r   r   r   r   r    r   r   r   r   )r   r#   r>   r   r&   r   r   r   Úupdate_batchf   s   

ýzUpdateQuery.update_batchc                 C   sš   g }|  ¡ D ]A\}}|  ¡  |¡}|jo|j  p|j }|jjj}|r*|jr0|j	r0t
d| ƒ‚||  ¡ jur?|  |||¡ q| |||f¡ q|  |¡S )z±
        Convert a dictionary of field name to value mappings into an update
        query. This is the entry point for the public update() method on
        querysets.
        zMCannot update model field %r (only non-relations and foreign keys permitted).)Úitemsr   Ú	get_fieldÚauto_createdÚconcreter4   r5   Úconcrete_modelÚis_relationÚmany_to_manyr   Úadd_related_updateÚappendÚadd_update_fields)r   r>   Ú
values_seqÚnameÚvalr%   Údirectr4   r   r   r   rS   m   s    
ÿÿ
zUpdateQuery.add_update_valuesc                 C   s@   |D ]\}}}t |dƒr|j| ddd�}| j |||f¡ qdS )zó
        Append a sequence of (field, model, value) triples to the internal list
        that will be used to generate the UPDATE query. Might be more usefully
        called add_update_targets() to hint at the extra information here.
        Úresolve_expressionFT)Úallow_joinsÚfor_saveN)Úhasattrrc   r>   r]   )r   r_   r%   r4   ra   r   r   r   r^   ƒ   s
   
üzUpdateQuery.add_update_fieldsc                 C   s   | j  |g ¡ |d|f¡ dS )zž
        Add (name, value) to an update query for an ancestor model.

        Update are coalesced so that only one update query per ancestor is run.
        N)rO   Ú
setdefaultr]   )r   r4   r%   Úvaluer   r   r   r\   �   s   zUpdateQuery.add_related_updatec                 C   sX   | j sg S g }| j  ¡ D ]\}}t|ƒ}||_| jdur$| d| jf¡ | |¡ q|S )zá
        Return a list of query objects: one for each update required to an
        ancestor model. Each query will have the same filtering conditions as
        the current query but will only update a single table.
        Nr0   )rO   rU   r
   r>   rN   Ú
add_filterr]   )r   Úresultr4   r>   r1   r   r   r   Úget_related_updates—   s   
zUpdateQuery.get_related_updates)r@   rA   rB   rC   rD   rH   rI   rP   rT   rS   r^   r\   rk   Ú__classcell__r   r   rL   r   r
   O   s    	r
   c                       s0   e Zd ZdZddœ‡ fdd„
Zddd„Z‡  ZS )	r   ÚSQLInsertCompilerF)Úignore_conflictsc                   s(   t ƒ j|i |¤Ž g | _g | _|| _d S rF   )rG   rH   ÚfieldsÚobjsrn   )r   rn   rJ   rK   rL   r   r   rH   ¬   s   
zInsertQuery.__init__c                 C   s   || _ || _|| _d S rF   )ro   rp   Úraw)r   ro   rp   rq   r   r   r   Úinsert_values²   s   
zInsertQuery.insert_values)F)r@   rA   rB   rD   rH   rr   rl   r   r   rL   r   r   ©   s    r   c                   @   s   e Zd ZdZdZdd„ ZdS )r   zu
    Take another query as a parameter to the FROM clause and only select the
    elements in the provided list.
    ÚSQLAggregateCompilerc                 C   s$   d|_ | |¡jdd�\| _ | _d S )NT)Úwith_col_aliases)Úsubqueryr   Úas_sqlÚ
sub_params)r   r1   r   r   r   r   Úadd_subqueryÀ   s   zAggregateQuery.add_subqueryN)r@   rA   rB   rC   rD   rx   r   r   r   r   r   ¸   s    r   N)rC   Údjango.core.exceptionsr   Ú	django.dbr   Údjango.db.models.query_utilsr   Údjango.db.models.sql.constantsr   r   r   Údjango.db.models.sql.queryr   Ú__all__r	   r
   r   r   r   r   r   r   Ú<module>   s    ?Z