o
    þÞhãP ã                   @   sà   d dl Z d dlZd dlmZ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mZmZ d dlmZ G dd„ deddƒƒZG dd„ dƒZ dS )é    N)ÚdefaultdictÚ
namedtuple)ÚEnum)ÚTopologicalSorter)Úchain)Úsettings)Úmodels)Ú
operations)Ú	Migration)ÚAlterModelOptions)ÚMigrationOptimizer)ÚMigrationQuestioner)ÚCOMPILED_REGEX_TYPEÚRegexObjectÚresolve_relation)Úcached_propertyc                   @   s4   e Zd ZG dd„ deƒZedd„ ƒZedd„ ƒZdS )ÚOperationDependencyc                   @   s    e Zd ZdZdZdZdZdZdS )zOperationDependency.Typer   é   é   é   é   N)Ú__name__Ú
__module__Ú__qualname__ÚCREATEÚREMOVEÚALTERÚREMOVE_ORDER_WRTÚALTER_FOO_TOGETHER© r   r   úa/var/www/html/premium_crap/venv/lib/python3.10/site-packages/django/db/migrations/autodetector.pyÚType   s    r!   c                 C   ó
   | j  ¡ S ©N)Ú
model_nameÚlower©Úselfr   r   r    Úmodel_name_lower!   ó   
z$OperationDependency.model_name_lowerc                 C   r"   r#   )Ú
field_namer%   r&   r   r   r    Úfield_name_lower%   r)   z$OperationDependency.field_name_lowerN)r   r   r   r   r!   r   r(   r+   r   r   r   r    r      s    
r   z$app_label model_name field_name typec                   @   sÀ  e Zd ZdZdjdd„Zdkdd„Zdd„ Zd	d
„ Zdldd„Zdd„ Z	dd„ Z
edd„ ƒZdjdd„Zdd„ Zdd„ Zdd„ Zdmdd„Zdd„ Zd d!„ Zd"d#„ Zd$d%„ Zd&d'„ Zd(d)„ Zd*d+„ Zd,d-„ Zd.d/„ Zd0d1„ Zd2d3„ Zd4d5„ Zd6d7„ Zd8d9„ Zd:d;„ Z d<d=„ Z!d>d?„ Z"d@dA„ Z#dBdC„ Z$dDdE„ Z%dFdG„ Z&dHdI„ Z'edJdK„ ƒZ(dLdM„ Z)dNdO„ Z*dPdQ„ Z+dRdS„ Z,dTdU„ Z-dVdW„ Z.dXdY„ Z/dZd[„ Z0d\d]„ Z1d^d_„ Z2d`da„ Z3dbdc„ Z4djddde„Z5dfdg„ Z6e7dhdi„ ƒZ8dS )nÚMigrationAutodetectora  
    Take a pair of ProjectStates and compare them to see what the first would
    need doing to make it match the second (the second usually being the
    project's current state).

    Note that this naturally operates on entire projects at a time,
    as it's likely that changes interact (for example, you can't
    add a ForeignKey without having a migration to add the table it
    depends on first). A user interface may offer single-app usage
    if it wishes, with the caveat that it may not always be possible.
    Nc                 C   s.   || _ || _|p
tƒ | _dd„ |jD ƒ| _d S )Nc                 S   s   h | ]\}}|’qS r   r   )Ú.0ÚappÚmodelr   r   r    Ú	<setcomp>;   s    z1MigrationAutodetector.__init__.<locals>.<setcomp>)Ú
from_stateÚto_stater   Ú
questionerr   Úexisting_apps)r'   r1   r2   r3   r   r   r    Ú__init__7   s   zMigrationAutodetector.__init__c                 C   s.   |   ||¡}|  |||¡}|r|  ||¡}|S )zÌ
        Main entry point to produce a list of applicable changes.
        Take a graph to base names on and an optional set of apps
        to try and restrict to (restriction is not guaranteed)
        )Ú_detect_changesÚarrange_for_graphÚ_trim_to_apps)r'   ÚgraphÚtrim_to_appsÚconvert_appsÚmigration_nameÚchangesr   r   r    r=   =   s
   zMigrationAutodetector.changesc                    s  t |tƒr‡ fdd„|D ƒS t |tƒrt‡ fdd„|D ƒƒS t |tƒr.‡ fdd„| ¡ D ƒS t |tjƒrB|jˆ  |j	¡ˆ  |j
¡fS t |tƒrKt|ƒS t |tƒrR|S t|dƒr�| ¡ }t |tjƒrg|dd	… }|\}}}|‡ fd
d„|D ƒ‡ fdd„| ¡ D ƒfS |S )zÈ
        Recursive deconstruction for a field and its arguments.
        Used for full comparison for rename/alter; sometimes a single-level
        deconstruction will not compare correctly.
        c                    ó   g | ]}ˆ   |¡‘qS r   ©Údeep_deconstruct©r-   Úvaluer&   r   r    Ú
<listcomp>P   ó    z:MigrationAutodetector.deep_deconstruct.<locals>.<listcomp>c                 3   s   � | ]}ˆ   |¡V  qd S r#   r?   rA   r&   r   r    Ú	<genexpr>R   s   € z9MigrationAutodetector.deep_deconstruct.<locals>.<genexpr>c                    ó   i | ]
\}}|ˆ   |¡“qS r   r?   ©r-   ÚkeyrB   r&   r   r    Ú
<dictcomp>T   ó    z:MigrationAutodetector.deep_deconstruct.<locals>.<dictcomp>Údeconstructr   Nc                    r>   r   r?   rA   r&   r   r    rC   i   rD   c                    rF   r   r?   rG   r&   r   r    rI   j   rJ   )Ú
isinstanceÚlistÚtupleÚdictÚitemsÚ	functoolsÚpartialÚfuncr@   ÚargsÚkeywordsr   r   ÚtypeÚhasattrrK   r   ÚField)r'   ÚobjÚdeconstructedÚpathrT   Úkwargsr   r&   r    r@   I   s2   




ý



ýz&MigrationAutodetector.deep_deconstructc                 C   sP   g }t | ¡ ƒD ]\}}|  |¡}|jr |jjr |d  dd¡ | |¡ q|S )zÒ
        Return a definition of the fields that ignores field names and
        what related fields actually relate to. Used for detecting renames (as
        the related fields change during renames).
        r   ÚtoN)ÚsortedrP   r@   Úremote_fieldr/   ÚpopÚappend)r'   ÚfieldsÚ
fields_defÚnameÚfieldÚdeconstructionr   r   r    Úonly_relation_agnostic_fieldso   s   
z3MigrationAutodetector.only_relation_agnostic_fieldsc                 C   sH  i | _ i | _i | _i | _tƒ | _tƒ | _tƒ | _tƒ | _tƒ | _	tƒ | _
| jj ¡ D ]3\\}}}|j dd¡s@| j ||f¡ q*|| jjvr]|j d¡rU| j ||f¡ q*| j ||f¡ q*| jj ¡ D ]9\\}}}|j dd¡sz| j
 ||f¡ qd|| jjvs†|r�||v r�|j d¡r•| j	 ||f¡ qd| j ||f¡ qd| j ¡  | j ¡  |  ¡  |  ¡  |  ¡  |  ¡  |  ¡  |  ¡  |  ¡  |  ¡  |  ¡  |  ¡  |  ¡  |  ¡  |   ¡  |  !¡  |  "¡  |  #¡  |  $¡  |  %¡  |  &¡  |  '¡  |  (¡  |  )¡  |  *¡  |  +¡  |  ,¡  |  -¡  |  .¡  |  /¡  |  0|¡ |  1¡  | j2S )aX  
        Return a dict of migration plans which will achieve the
        change from from_state to to_state. The dict has app labels
        as keys and a list of migrations as values.

        The resulting migrations aren't specially named, but the names
        do matter for dependencies inside the set.

        convert_apps is the list of apps to convert to use migrations
        (i.e. to make initial migrations for, in the usual case)

        graph is an optional argument that, if provided, can help improve
        dependency generation and avoid potential circular dependencies.
        ÚmanagedTÚproxy)3Úgenerated_operationsÚaltered_indexesÚaltered_constraintsÚrenamed_fieldsÚsetÚold_model_keysÚold_proxy_keysÚold_unmanaged_keysÚnew_model_keysÚnew_proxy_keysÚnew_unmanaged_keysr1   r   rP   ÚoptionsÚgetÚaddÚ	real_appsr2   Úresolve_fields_and_relationsÚgenerate_renamed_modelsÚ_prepare_field_listsÚ_generate_through_model_mapÚgenerate_deleted_modelsÚgenerate_created_modelsÚgenerate_deleted_proxiesÚgenerate_created_proxiesÚgenerate_altered_optionsÚgenerate_altered_managersÚ!generate_altered_db_table_commentÚcreate_renamed_fieldsÚcreate_altered_indexesÚcreate_altered_constraintsÚgenerate_removed_constraintsÚgenerate_removed_indexesÚgenerate_renamed_fieldsÚgenerate_renamed_indexesÚ(generate_removed_altered_unique_togetherÚgenerate_removed_fieldsÚgenerate_added_fieldsÚgenerate_altered_fieldsÚ&generate_altered_order_with_respect_toÚ generate_altered_unique_togetherÚgenerate_added_indexesÚgenerate_added_constraintsÚgenerate_altered_constraintsÚgenerate_altered_db_tableÚ_sort_migrationsÚ_build_migration_listÚ_optimize_migrationsÚ
migrations)r'   r;   r9   Ú	app_labelr$   Úmodel_stater   r   r    r6   }   s|   €ÿ€


z%MigrationAutodetector._detect_changesc                    s`   ˆ j ˆ j@ ˆ _ˆ jˆ j@ ˆ _ˆ jˆ j@ ˆ _i ˆ _	‡ fdd„ˆ jD ƒˆ _
‡ fdd„ˆ jD ƒˆ _dS )zÏ
        Prepare field lists and a list of the fields that used through models
        in the old state so dependencies can be made from the through model
        deletion to the field that uses it.
        c                    s@   h | ]\}}ˆ j j|ˆ j ||f|¡f jD ]}|||f’qqS r   )r1   r   Úrenamed_modelsrv   rb   ©r-   r™   r$   r*   r&   r   r    r0   ñ   s    ÿûþÿz=MigrationAutodetector._prepare_field_lists.<locals>.<setcomp>c                    s2   h | ]\}}ˆ j j||f jD ]}|||f’qqS r   )r2   r   rb   rœ   r&   r   r    r0   ø   s    ýþÿN)ro   rr   Úkept_model_keysrp   rs   Úkept_proxy_keysrq   rt   Úkept_unmanaged_keysÚthrough_usersÚold_field_keysÚnew_field_keysr&   r   r&   r    r{   ç   s   
þ
þz*MigrationAutodetector._prepare_field_listsc                 C   s†   t | jƒD ];\}}| j ||f|¡}| jj||f }|j ¡ D ] \}}t|dƒr?t	|j
ddƒr?t|j
j||ƒ}|||f| j|< qqdS )zThrough model map generation.r_   ÚthroughN)r^   ro   r›   rv   r1   r   rb   rP   rW   Úgetattrr_   r   r£   r    )r'   r™   r$   Úold_model_nameÚold_model_stater*   re   Úthrough_keyr   r   r    r|   þ   s&   ÿÿ
ÿ
ý€ùûz1MigrationAutodetector._generate_through_model_mapc                 C   sB   | j dkr	| dfS tt| jƒ d¡\}}t|| ¡ | j| jƒdfS )zp
        Return the resolved dependency and a boolean denoting whether or not
        it was swappable.
        Ú__setting__FÚ.T)	r™   r¤   r   r$   Úsplitr   r%   r*   rV   )Ú
dependencyÚresolved_app_labelÚresolved_object_namer   r   r    Ú_resolve_dependency  s   
ÿþüùz)MigrationAutodetector._resolve_dependencyc                 C   sF  i | _ tdd„ | j ¡ D ƒƒ}d}|�r!t| jƒD ]ã}g }tƒ }t| j| ƒD ]Š}d}tƒ }	|jD ]l}
|
}|  |
¡\}
}|
j	|kr�| j 
|
j	g ¡D ]}|  ||
¡rUd} nqI|sZ nD|rf|	 |j	|jf¡ q1|
j	| j v r||	 |
j	| j |
j	 d jf¡ q1|r›|r’| |
j	¡r’|	 | |
j	¡d ¡ q1|	 |
j	df¡ q1d}q1|r±| |¡ | |	¡ | j| d= q' |s¶|rü| j| r½|ròtdtfg g d	œƒ}|d
t| j  
|g ¡ƒd  |ƒ}t|ƒ|_||_|| jv|_| j  |g ¡ |¡ d}q|| j|  | j|< qtdd„ | j ¡ D ƒƒ}||k�r|�sd}ntd| j ƒ‚|}|sdS dS )ag  
        Chop the lists of operations up into migrations with dependencies on
        each other. Do this by going through an app's list of operations until
        one is found that has an outgoing dependency that isn't in another
        app's migration yet (hasn't been chopped off its list). Then chop off
        the operations before it into a migration and move onto the next app.
        If the loops completes without doing anything, there's a circular
        dependency (which _should_ be impossible as the operations are
        all split at this point so they can't depend and be depended on).
        c                 s   ó   � | ]}t |ƒV  qd S r#   ©Úlen©r-   Úxr   r   r    rE   3  ó   € z>MigrationAutodetector._build_migration_list.<locals>.<genexpr>FTéÿÿÿÿr   Ú	__first__r
   )r	   Údependencieszauto_%ir   c                 s   r¯   r#   r°   r²   r   r   r    rE   ”  r´   z)Cannot resolve operation dependencies: %rN)r˜   Úsumrj   Úvaluesr^   rn   rM   Ú
_auto_depsr®   r™   rv   Úcheck_dependencyrw   r$   rd   Ú
leaf_nodesra   ÚupdaterV   r
   r±   r·   r	   r4   ÚinitialÚ
setdefaultÚ
ValueError)r'   r9   Únum_opsÚ	chop_moder™   Úchoppedr·   Ú	operationÚdeps_satisfiedÚoperation_dependenciesÚdepÚoriginal_depÚis_swappable_depÚother_operationÚsubclassÚinstanceÚnew_num_opsr   r   r    r–   '  s    

ÿþþÿþÿÿÿ€

ýþ
ÿ€
ÿÿ˜z+MigrationAutodetector._build_migration_listc                    s�   t ˆj ¡ ƒD ]>\}}tƒ }|D ]+}| |¡ |jD ] ‰ ˆ ˆ ¡d ‰ ˆ j|kr)q|j|g‡ ‡fdd„|D ƒ¢R Ž  qqt| 	¡ ƒˆj|< qdS )z{
        Reorder to make things possible. Reordering may be needed so FKs work
        nicely inside the same app.
        r   c                 3   s    � | ]}ˆ  |ˆ ¡r|V  qd S r#   )r»   r²   ©rÇ   r'   r   r    rE   ®  s   € z9MigrationAutodetector._sort_migrations.<locals>.<genexpr>N)
r^   rj   rP   r   rw   rº   r®   r™   rM   Ústatic_order)r'   r™   ÚopsÚtsÚopr   rÎ   r    r•   Ÿ  s   


$úõz&MigrationAutodetector._sort_migrationsc                 C   s    | j  ¡ D ]\}}t||dd … ƒD ]\}}|j ||jf¡ qq| j  ¡ D ]}|D ]
}tt|jƒƒ|_q*q&| j  ¡ D ]\}}|D ]}t	ƒ  
|j|¡|_qAq;d S )Nr   )r˜   rP   Úzipr·   ra   rd   r¹   rM   rn   r   Úoptimizer	   )r'   r™   r˜   Úm1Úm2Ú	migrationr   r   r    r—   ±  s   ÿÿÿÿÿz*MigrationAutodetector._optimize_migrationsc                    sÌ  ˆ j du rˆ jtjjkrt|tjƒo|jˆ j	kS ˆ j durNˆ jtjjkrNt|tjƒo;|jˆ j	ko;t
‡ fdd„|jD ƒƒpMt|tjƒoM|j	ˆ j	koM|jˆ jkS ˆ j durlˆ jtjjkrlt|tjƒok|j	ˆ j	kok|jˆ jkS ˆ j du r„ˆ jtjjkr„t|tjƒoƒ|jˆ j	kS ˆ j dur¢ˆ jtjjkr¢t|tjƒo¡|j	ˆ j	ko¡|jˆ jkS ˆ j durÄˆ jtjjkrÄt|tjƒoÃ|jˆ j	koÃ|jp¾d ¡ ˆ jkS ˆ j durßˆ jtjjkrßt|tjtjfƒoÞ|jˆ j	kS tdˆ f ƒ‚)zn
        Return True if the given operation depends on the given dependency,
        False otherwise.
        Nc                 3   s   � | ]
\}}ˆ j |kV  qd S r#   )r*   )r-   r³   Úy©r«   r   r    rE   Ù  s   € z9MigrationAutodetector.check_dependency.<locals>.<genexpr>Ú zCan't handle dependency %r)r*   rV   r   r!   r   rL   r	   ÚCreateModelÚ
name_lowerr(   Úanyrb   ÚAddFieldr+   r   ÚRemoveFieldÚDeleteModelr   Ú
AlterFieldr   ÚAlterOrderWithRespectToÚorder_with_respect_tor%   r   ÚAlterUniqueTogetherÚAlterIndexTogetherrÀ   )r'   rÄ   r«   r   rÙ   r    r»   Ã  sl   

þ

ÿý
ÿ
ù

ÿ
ý

þ

ÿ
ý

ÿÿý

þ
û	z&MigrationAutodetector.check_dependencyFc                 C   s@   |pg |_ |r| j |g ¡ d|¡ d S | j |g ¡ |¡ d S )Nr   )rº   rj   r¿   Úinsertra   )r'   r™   rÄ   r·   Ú	beginningr   r   r    Úadd_operation  s   
z#MigrationAutodetector.add_operationc                 C   s”   z?| j j| }dd„ |jD ƒ}d|d |d f }|j d¡s0d|v s0d|v s0tj ¡ | ¡ kr=d	|d  d	|d  fW S W |S  tyI   Y |S w )
z|
        Place potential swappable models first in lists of created models (only
        real way to solve #22783).
        c                 S   s    h | ]}t |tƒr|n|j’qS r   )rL   Ústrr   )r-   Úbaser   r   r    r0   '  ó    ÿÿz<MigrationAutodetector.swappable_first_key.<locals>.<setcomp>ú%s.%sr   r   Ú	swappableÚAbstractUserÚAbstractBaseUserÚ___)	r2   r   Úbasesru   rv   r   ÚAUTH_USER_MODELr%   ÚLookupError)r'   Úitemrš   Ú
base_namesÚstring_versionr   r   r    Úswappable_first_key   s$   þ
ÿþþþz)MigrationAutodetector.swappable_first_keyc                 C   sl  i | _ i | _| j| j }t|ƒD ]£\}}| jj||f }|  |j¡}| j| j }|D ]ˆ\}}||kr²| j	j||f }	|  |	j¡}
||
kr²| j
 |	|¡r²g }t|j ¡ ƒdd„ | jj||f  ¡ D ƒ }|D ]}|jrv| |  |||| j¡¡ qe| j|tj|	j|jd�|d� || j ||f< d|	j|	jf }d|j|jf | j|< | j ||f¡ | j ||f¡  nq*qdS )z¼
        Find any renamed models, generate the operations for them, and remove
        the old entry from the model lists. Must be run before other
        model-level generation.
        c                 S   s    g | ]}|  ¡ D ]}|j‘qqS r   )r¹   r_   )r-   Ú	relationsre   r   r   r    rC   R  s    ûüÿzAMigrationAutodetector.generate_renamed_models.<locals>.<listcomp>)Úold_nameÚnew_name©r·   rì   N)r›   Úrenamed_models_relrr   ro   r^   r2   r   rg   rb   r1   r3   Úask_rename_modelrM   r¹   rø   Úis_relationÚextendÚ!_get_dependencies_for_foreign_keyrè   r	   ÚRenameModelrd   r™   rÜ   Úremoverw   )r'   Úadded_modelsr™   r$   rš   Úmodel_fields_defÚremoved_modelsÚrem_app_labelÚrem_model_nameÚrem_model_stateÚrem_model_fields_defr·   rb   re   Úrenamed_models_rel_keyr   r   r    rz   7  sz   ÿÿÿÿüüÿ€þúþþÿÿ€Çz-MigrationAutodetector.generate_renamed_modelsc                    sþ  | j | jB }| j| }| j| }tt|| jdd�t|| jdd�ƒ}|D �]Ø\‰ ‰| jjˆ ˆf }i ‰d}|j	 
¡ D ]&\}}|jr_|jjrT|jrL|jj}n|jjsT|ˆ|< t|jddƒr_|ˆ|< q9|j d¡}	|j d¡}
|j dd¡}|j dd¡}tˆ ˆdtjjƒg}|jD ]S}t|tƒrÚd	|v rÚ| d	d
¡\}}| t||dtjjƒ¡ | jj ||f¡}| jj ||f¡}|rÚ|rÚt|j	ƒ |j	¡ |j	¡}|D ]}| t|||tjjƒ¡ qËq‡|rñ| tg t |ˆ ˆƒ¢d‘tjj‘R Ž ¡ | j!ˆ t"j#|j$‡fdd„|j	 
¡ D ƒ|j|j|j%d�|dd� |j dd¡�sq#tˆ 
¡ ƒD ],\}}|  &ˆ ˆ|| j¡}| tˆ ˆdtjjƒ¡ | j!ˆ t"j'ˆ||d�t(t|ƒƒd� �q|�rl| j!ˆ t"j)ˆ|d�tˆ ˆ|tjjƒtˆ ˆdtjjƒgd� ‡ ‡fdd„tˆƒD ƒ}| tˆ ˆdtjjƒ¡ |	D ]}| j!ˆ t"j*ˆ|d�|d� �q†|
D ]}| j!ˆ t"j+ˆ|d�|d� �q™|�rº| j!ˆ t"j,ˆ|d�|d� | jj-}ˆ ˆf| j.v �rü|ˆ ˆf  
¡ D ]-\}‰| jj| }ˆ 
¡ D ]\}}| j!|j/t"j0|j$||d�tˆ ˆdtjjƒgd� �qÜ�qÎq#dS )ar  
        Find all new models (both managed and unmanaged) and make create
        operations for them as well as separate operations to create any
        foreign key or M2M relationships (these are optimized later, if
        possible).

        Defer any model options that refer to collections of fields that might
        be deferred (e.g. unique_together).
        T)rH   ÚreverseNr£   ÚindexesÚconstraintsÚunique_togetherrã   r©   r   c                    s   g | ]
}|d  ˆ vr|‘qS )r   r   ©r-   Úd)Úrelated_fieldsr   r    rC   Û  s
    þzAMigrationAutodetector.generate_created_models.<locals>.<listcomp>©rd   rb   ru   rñ   Úmanagers)r·   rç   rh   ©r$   rd   re   rû   ©rd   rã   c                    s   g | ]}t ˆ ˆ|t jjƒ‘qS r   )r   r!   r   )r-   rd   )r™   r$   r   r    rC     s    ýÿÿ©r$   Úindex©r$   Ú
constraint©rd   r  )1ro   rq   rr   rt   r   r^   r÷   r2   r   rb   rP   r_   r/   Úprimary_keyÚparent_linkr¤   ru   r`   r   r!   r   rñ   rL   ré   rª   ra   r   r1   rv   rn   Ú
differenceÚintersectionr   rè   r	   rÛ   rd   r  r   rÞ   rM   râ   ÚAddIndexÚAddConstrainträ   rø   rp   r™   rá   )r'   Úold_keysr  Úadded_unmanaged_modelsÚall_added_modelsrš   Úprimary_key_relr*   re   r  r  r  rã   r·   rê   Úbase_app_labelÚ	base_nameÚold_base_model_stateÚnew_base_model_stateÚremoved_base_fieldsÚremoved_base_fieldrd   Úrelated_dependenciesr  r  rø   Úrelated_model_keyÚrelated_model_stateÚrelated_field_nameÚrelated_fieldr   )r™   r$   r  r    r~   {  s‚  


þ
€ÿÿÿ
üÿ
ÿÿÿûüÿ€	
ÿþýÿ
þ÷òüÿÿý

ù
þüÿùúüÿÿþ
úþ
úþú
ÿ
þýüÿ
ùÿ€ �Åz-MigrationAutodetector.generate_created_modelsc           	   
   C   sÄ   | j | j }t|ƒD ]U\}}| jj||f }|j d¡sJ ‚t||dtjj	ƒg}|j
D ]}t|tƒrJd|v rJ| dd¡\}}| t||dtjjƒ¡ q+| j|tj|jg |j|j
|jd�|d� q
dS )zó
        Make CreateModel statements for proxy models. Use the same statements
        as that way there's less code duplication, but for proxy models it's
        safe to skip all the pointless field stuff and chuck out an operation.
        ri   Nr©   r   r  rû   )rs   rp   r^   r2   r   ru   rv   r   r!   r   rñ   rL   ré   rª   ra   r   rè   r	   rÛ   rd   r  )	r'   Úaddedr™   r$   rš   r·   rê   r%  r&  r   r   r    r€   X  s@   ÿÿ
üÿ€	ûöêz.MigrationAutodetector.generate_created_proxiesc              
   C   sÐ  | j | jB }| j| }| j| }tt|ƒt|ƒƒ}|D ]Ê\}}| jj||f }i }|j 	¡ D ]\}	}
|
j
rH|
j
jr=|
||	< t|
j
ddƒrH|
||	< q.|j dd¡}|r]|  |tj|dd�¡ t|ƒD ]}|  |tj||d�¡ qag }| jj}|||f  	¡ D ]*\\}}}| 	¡ D ]\}	}
| t|||	tjjƒ¡ |
js¦| t|||	tjjƒ¡ q‡q}t|ƒD ]}| t|||tjjƒ¡ q¬| j ||jf¡}|rÔ| tg |¢tjj‘R Ž ¡ | j|tj|jd�tt |ƒƒd� qdS )a†  
        Find all deleted models (managed and unmanaged) and make delete
        operations for them as well as separate operations to delete any
        foreign key or M2M relationships (these are optimized later, if
        possible).

        Also bring forward removal of any model options that refer to
        collections of fields - the inverse of generate_created_models().
        r£   Nr  r  ©r$   rd   ©rd   rû   )!rr   rt   ro   rq   r   r^   r1   r   rb   rP   r_   r/   r¤   ru   r`   rè   r	   rä   rß   rø   ra   r   r!   r   Úmany_to_manyr   r    rv   rÜ   rà   rd   rM   rn   )r'   Únew_keysÚdeleted_modelsÚdeleted_unmanaged_modelsÚall_deleted_modelsr™   r$   rš   r  r*   re   r  rd   r·   rø   Úrelated_object_app_labelÚobject_nameÚrelation_related_fieldsÚthrough_userr   r   r    r}   ‚  sž   


ÿ€þþþþýüÿüÿ€öÿÿÿÿ
û¹z-MigrationAutodetector.generate_deleted_modelsc                 C   sX   | j | j }t|ƒD ]\}}| jj||f }|j d¡sJ ‚|  |tj	|j
d�¡ q
dS )z*Make DeleteModel options for proxy models.ri   r2  N)rp   rs   r^   r1   r   ru   rv   rè   r	   rà   rd   )r'   Údeletedr™   r$   rš   r   r   r    r   á  s   ÿþýz.MigrationAutodetector.generate_deleted_proxiesc                 C   s¦  g | _ | j ¡ }t| j| ƒD ]Á\}}}| j ||f|¡}| jj||f }| j	j||f }| 
|¡}|  |¡}	t|| j ƒD ]‘\}
}}|
|krÏ||krÏ| 
|¡}|  |¡}|jrv|jjrvd|d v rv|d d }|| jv rv| j| |d d< | |¡ | ¡ d }||	ks�|dd… |	dd… krÏt|d |d�|	d krÏ| j ||||¡rÏ| j  |
||j|||||f¡ | |
||f¡ | |||f¡ || j|||f<  nq>qdS )zWork out renamed fields.r]   r   r   r   )Ú	db_columnN)Úrenamed_operationsr¡   Úcopyr^   r¢   r›   rv   r1   r   r2   Ú	get_fieldr@   r_   r/   rü   Úset_attributes_from_nameÚget_attname_columnrO   r3   Ú
ask_renamera   r=  r  rw   rm   )r'   r¡   r™   r$   r*   r¥   r¦   Únew_model_statere   Ú	field_decr  r  Úrem_field_nameÚ	old_fieldÚold_field_decÚ
old_rel_toÚold_db_columnr   r   r    r„   î  sp   
ÿÿ

ÿ

ÿþ

ÿÿøÿÿÿ€Èz+MigrationAutodetector.create_renamed_fieldsc           
   	   C   sŒ   | j D ]@\}}}}}}}}||jkr%| ¡ }	||	_|  |tj|||	d�¡ |  |tj|||d�¡ | j 	|||f¡ | j 
|||f¡ qdS )z Generate RenameField operations.r  )r$   rù   rú   N)r>  r=  Úclonerd   rè   r	   rá   ÚRenameFieldr¡   r  rw   )
r'   r  r  Úrem_db_columnrF  r™   r$   re   r*   Úaltered_fieldr   r   r    r‰   ,  s@   ÷
ýþýþßz-MigrationAutodetector.generate_renamed_fieldsc                 C   ó.   t | j| j ƒD ]\}}}|  |||¡ qdS )zMake AddField operations.N)r^   r¢   r¡   Ú_generate_added_field©r'   r™   r$   r*   r   r   r    r�   Q  ó
   
ÿýz+MigrationAutodetector.generate_added_fieldsc           	      C   sN  | j j||f  |¡}t|||tjjƒg}|jr(|jjr(| |  	|||| j ¡¡ |j
r3| |  |¡¡ tjtjtjf}tjtjtjf}|jpc| ¡ pc| ¡ pc|jpc|joV|jpct||ƒo^|jpct||ƒ}|sƒ| ¡ }t||ƒr{|jr{| j ||¡|_n| j ||¡|_|j r–| ¡ r–t!|jƒr–| j "||¡ | j#|t$j%||||d�|d� d S )N©r$   rd   re   Úpreserve_defaultrû   )&r2   r   r@  r   r!   r   r_   r/   rÿ   r   Ú	generatedÚ%_get_dependencies_for_generated_fieldÚ	DateFieldÚDateTimeFieldÚ	TimeFieldÚ	AutoFieldÚSmallAutoFieldÚBigAutoFieldÚnullÚhas_defaultÚhas_db_defaultr3  ÚblankÚempty_strings_allowedrL   Úauto_nowrK  Úauto_now_addr3   Úask_auto_now_add_additionÚdefaultÚask_not_null_additionÚuniqueÚcallableÚ$ask_unique_callable_default_additionrè   r	   rÞ   )	r'   r™   r$   r*   re   r·   Útime_fieldsÚauto_fieldsrT  r   r   r    rP  X  sh   ÿÿüÿÿþý
üûù	ÿÿü
øz+MigrationAutodetector._generate_added_fieldc                 C   rO  )zMake RemoveField operations.N)r^   r¡   r¢   Ú_generate_removed_fieldrQ  r   r   r    rŒ   �  rR  z-MigrationAutodetector.generate_removed_fieldsc              	   C   s>   | j |tj||d�t|||tjjƒt|||tjjƒgd� d S )Nr1  rû   )rè   r	   rß   r   r!   r   r   rQ  r   r   r    rl  —  s(   þüüù
÷z-MigrationAutodetector._generate_removed_fieldc              	      s¬  t ˆjˆj@ ƒD �]J\}}}ˆj ||f|¡}ˆj |||f|¡}ˆjj||f  |¡}ˆj	j||f  |¡}g }t
|dƒr½t|jddƒr½t|jj||ƒ‰ˆˆjv rX|jj|j_t|jddƒ}	|	rwˆ|	f }
|
ˆjv rw|jj|j_|jj|j_t|ddƒ}|r±||f‰ t‡ ‡fdd„|D ƒƒ|_t‡‡fdd„|jD ƒƒ|_t|ddƒ }r±t|ƒ|_t|jƒ|_| ˆ |||ˆj	¡¡ t
|dƒrÜt|jd	dƒrÜt|jj||ƒ‰ˆˆjv rÜ|jj|j_ˆ |¡}ˆ |¡}||k�rS||k�rS|joõ|j}|j oý|j }|�s|�rEd
}|j�r3|j�s3| ¡ �s3| ¡ �s3|j�s3| ¡ }ˆj ||¡}|tju�r2||_d}n|}ˆj |t!j"||||d�|d� qˆ #|||¡ ˆ $|||¡ qdS )zp
        Make AlterField operations, or possibly RemovedField/AddField if alter
        isn't possible.
        r_   r/   Nr*   Úfrom_fieldsc                    ó    g | ]}ˆj  ˆ |f |¡‘qS r   ©rm   rv   )r-   Ú
from_field)Úfrom_rename_keyr'   r   r    rC   â  s    ý
ÿÿzAMigrationAutodetector.generate_altered_fields.<locals>.<listcomp>c                    rn  r   ro  )r-   Úto_field)Ú
rename_keyr'   r   r    rC   ê  rë   r£   TFrS  rû   )%r^   r¡   r¢   r›   rv   rm   r1   r   r@  r2   rW   r¤   r_   r   r/   r*   rN   rm  Ú	to_fieldsrÿ   r   r£   r@   r3  r]  r^  r_  rK  r3   Úask_not_null_alterationÚNOT_PROVIDEDre  rè   r	   rá   rl  rP  )r'   r™   r$   r*   r¥   Úold_field_namerG  Ú	new_fieldr·   Úremote_field_nameÚto_field_rename_keyrm  Úold_from_fieldsrH  Únew_field_decÚboth_m2mÚneither_m2mrT  re   Únew_defaultr   )rq  rs  r'   r    rŽ   ±  sÎ   
ÿÿ
ÿÿÿÿ
ÿ


ÿüÿþÿ
üÿÿ
ÿ


ÿþýüûÿ€üø€Œz-MigrationAutodetector.generate_altered_fieldsc                    s&  t jj}ttƒ| _t| jƒD �]\}}| j 	||f|¡}| j
j||f }| jj||f }|j| ‰|j| ‰ ‡fdd„ˆ D ƒ}‡ fdd„ˆD ƒ}g }	g ‰g ‰|D ]7}
|
 ¡ }|d  d¡}|D ]'}| ¡ }|d  d¡}||kr†||kr†|	 ||d f¡ ˆ |
¡ ˆ |¡ q_qP|  t jj¡D ]`\}}}}}||ksž||krŸq�| |¡}|D ]H}g }|D ]}
|
 ¡ \}}}|sË|
jt|ƒkrËt|ƒddhkrË| |
¡ q¬t|ƒdkrî|d }ˆ |¡ |	 d |j|f¡ | j||f  |¡ q¦q�‡fd	d„|D ƒ}‡fd
d„|D ƒ}| j ||f|||	dœi¡ qd S )Nc                    ó   g | ]}|ˆ vr|‘qS r   r   ©r-   Úidx)Úold_indexesr   r    rC   9  ó    z@MigrationAutodetector.create_altered_indexes.<locals>.<listcomp>c                    r€  r   r   r�  )Únew_indexesr   r    rC   :  r„  r   rd   rb   r   r   c                    r€  r   r   r�  )Úremove_from_addedr   r    rC   t  ó    c                    r€  r   r   r�  )Úremove_from_removedr   r    rC   w  r‡  )Úadded_indexesÚremoved_indexesÚrenamed_indexes)r	   r  Úoption_namer   rM   Úrenamed_index_together_valuesr^   r�   r›   rv   r1   r   r2   ru   rK   r`   ra   Ú$_get_altered_foo_together_operationsrå   r  rb   rn   r±   rd   rk   r½   )r'   rŒ  r™   r$   r¥   r¦   rD  r‰  rŠ  r‹  Ú	new_indexÚnew_index_decÚnew_index_nameÚ	old_indexÚold_index_decÚold_index_nameÚ	old_valueÚ	new_valueÚindex_together_app_labelÚindex_together_model_namer·   Úremoved_valuesÚremoved_index_togetherÚrenamed_index_together_indexesÚ_rT   r\   Úrenamed_indexr   )r…  rƒ  r†  rˆ  r    r…   ,  sœ   
ÿ



€öÿú
ÿ
€

ÿÿ€ì
ÿ
ÿýÿÿµz,MigrationAutodetector.create_altered_indexesc                 C   óP   | j  ¡ D ] \\}}}|  ||¡}|d D ]}| j|tj||d�|d� qqd S )Nr‰  r  rû   )rk   rP   Ú_get_dependencies_for_modelrè   r	   r  )r'   r™   r$   Úalt_indexesr·   r  r   r   r    r‘   …  s   þúÿþz,MigrationAutodetector.generate_added_indexesc              	   C   óB   | j  ¡ D ]\\}}}|d D ]}|  |tj||jd�¡ qqd S )NrŠ  r1  )rk   rP   rè   r	   ÚRemoveIndexrd   )r'   r™   r$   r   r  r   r   r    rˆ   ’  s   þþÿÿz.MigrationAutodetector.generate_removed_indexesc                 C   sJ   | j  ¡ D ]\\}}}|d D ]\}}}|  |tj||||d�¡ qqd S )Nr‹  )r$   rú   rù   Ú
old_fields)rk   rP   rè   r	   ÚRenameIndex)r'   r™   r$   r   r”  r‘  r£  r   r   r    rŠ   �  s   ÿüþýÿz.MigrationAutodetector.generate_renamed_indexesc           
      C   s`   |  ¡ \}}}|  ¡ \}}}|jD ]}	| |	d ¡ q|jD ]}	| |	d ¡ q|||f|||fkS r#   )rK   Únon_db_attrsr`   )
r'   Úold_constraintÚnew_constraintÚold_pathÚold_argsÚ
old_kwargsÚnew_pathÚnew_argsÚ
new_kwargsÚattrr   r   r    Ú+_constraint_should_be_dropped_and_recreated¬  s   

zAMigrationAutodetector._constraint_should_be_dropped_and_recreatedc                    s  t jj}t| jƒD ]z\}}| j ||f|¡}| jj||f }| j	j||f }|j
| ‰|j
| ‰g }g ‰ ˆD ]*}ˆD ]%}	| ¡ }
|	 ¡ }|
|kr_|j|	jkr_|  ||	¡s_| |	¡ ˆ  |	j¡ q:q6‡ ‡fdd„ˆD ƒ}‡ ‡fdd„ˆD ƒ}| j ||f|||dœi¡ q	d S )Nc                    ó"   g | ]}|ˆvr|j ˆ vr|‘qS r   r2  ©r-   Úc)Úalt_constraints_nameÚold_constraintsr   r    rC   Ö  ó
    þzDMigrationAutodetector.create_altered_constraints.<locals>.<listcomp>c                    r°  r   r2  r±  )r³  Únew_constraintsr   r    rC   Û  rµ  )Úadded_constraintsÚremoved_constraintsrl   )r	   r   rŒ  r^   r�   r›   rv   r1   r   r2   ru   rK   rd   r¯  ra   rl   r½   )r'   rŒ  r™   r$   r¥   r¦   rD  Úalt_constraintsÚold_cÚnew_cÚ	old_c_decÚ	new_c_decÚadd_constraintsÚrem_constraintsr   )r³  r¶  r´  r    r†   ¹  sP   ÿ

ÿÿ
€õþþýÿÿÚz0MigrationAutodetector.create_altered_constraintsc                 C   rž  )Nr·  r  rû   )rl   rP   rŸ  rè   r	   r   ©r'   r™   r$   r¹  r·   r  r   r   r    r’   ë  s"   ýþúÿûz0MigrationAutodetector.generate_added_constraintsc              	   C   r¡  )Nr¸  r1  )rl   rP   rè   r	   ÚRemoveConstraintrd   )r'   r™   r$   r¹  r  r   r   r    r‡   û  s   ýþþÿüz2MigrationAutodetector.generate_removed_constraintsc              	   C   sT   | j  ¡ D ]"\\}}}|  ||¡}|d D ]}| j|tj||j|d�|d� qqd S )Nrl   )r$   rd   r  rû   )rl   rP   rŸ  rè   r	   ÚAlterConstraintrd   rÀ  r   r   r    r“   	  s$   ýýùÿûz2MigrationAutodetector.generate_altered_constraintsc                    sê   d }t ˆ jdƒrˆ jj}n(|j| |f }| ¡ D ]\\}}}t‡ fdd„| ¡ D ƒƒr4|› d|› �} nqtˆ dd ƒ}	|	d urDd}
|	}nt|| |ƒ\}
}t	|
|d t	j
jƒg}tˆ jdd ƒrstˆ jj| |ƒ\}}| t	||d t	j
jƒ¡ |S )Nr/   c                 3   s   � | ]}ˆ |j kV  qd S r#   )r_   )r-   r/  ©re   r   r    rE   "  s
   € ÿ
ÿzJMigrationAutodetector._get_dependencies_for_foreign_key.<locals>.<genexpr>r©   Úswappable_settingr¨   r£   )rW   r_   r/   rø   rP   rÝ   r¹   r¤   r   r   r!   r   r£   ra   )r™   r$   re   Úproject_stateÚremote_field_modelrø   Úremote_app_labelÚremote_model_namerb   rÄ  Údep_app_labelÚdep_object_namer·   Úthrough_app_labelÚthrough_object_namer   rÃ  r    r     sN   
þûýÿÿýüÿz7MigrationAutodetector._get_dependencies_for_foreign_keyc           	      C   s~   g }t  |j¡j}t| j| j ƒ}|D ])\}}}| jj ||f  |¡}|j	r*|j	j
s/|j|v r<| t|||jtjjƒ¡ q|S r#   )r   ÚQÚ
expressionÚreferenced_base_fieldsr^   r¢   r¡   r2   r@  r_   r/   rd   ra   r   r!   r   )	r'   re   r·   rÏ  Únewly_added_fieldsr™   r$   Úadded_field_nameÚadded_fieldr   r   r    rV  H  s,   ÿÿÿ
üÿ€z;MigrationAutodetector._get_dependencies_for_generated_fieldc              	   C   sF   g }| j j||f }|j ¡ D ]}|jr | |  |||| j ¡¡ q|S )z3Return foreign key dependencies of the given model.)r2   r   rb   r¹   rþ   rÿ   r   )r'   r™   r$   r·   rš   re   r   r   r    rŸ  ]  s   üÿ€z1MigrationAutodetector._get_dependencies_for_modelc                 #   sö   � t ˆjƒD ]r\‰ ‰ˆj ˆ ˆfˆ¡}ˆjjˆ |f }ˆjjˆ ˆf }|j |¡}|r6‡ ‡‡fdd„|D ƒntƒ }|j |¡}|rEt|ƒntƒ }||krxg }|D ]}|D ]}	| 	|	¡}
|
j
rn|
j
jrn| ˆ ˆ ˆ|
ˆj¡¡ qTqP||ˆ ˆ|fV  qd S )Nc                    s&   h | ]}t ‡ ‡‡fd d„|D ƒƒ’qS )c                 3   s$   � | ]}ˆj  ˆ ˆ|f|¡V  qd S r#   ro  )r-   Ún©r™   r$   r'   r   r    rE   y  s
   € ÿ
ÿzWMigrationAutodetector._get_altered_foo_together_operations.<locals>.<setcomp>.<genexpr>)rN   )r-   rg  rÔ  r   r    r0   x  s    üþÿzMMigrationAutodetector._get_altered_foo_together_operations.<locals>.<setcomp>)r^   r�   r›   rv   r1   r   r2   ru   rn   r@  r_   r/   rÿ   r   )r'   rŒ  r¥   r¦   rD  r•  r–  r·   Úfoo_togethersr*   re   r   rÔ  r    rŽ  m  sP   €ÿ	ùû÷
üÿ€ýû€Úz:MigrationAutodetector._get_altered_foo_together_operationsc                    sv   ˆ  |j¡D ]2\}}‰ ‰}|tjkr‡ ‡‡fdd„|D ƒ}| |¡}|s&|r8ˆjˆ |ddˆi|j|i¤Ž|d� qd S )Nc                    s"   h | ]}|ˆj ˆ ˆf vr|’qS r   )r�  rA   rÔ  r   r    r0   ¥  s    ÿþzOMigrationAutodetector._generate_removed_altered_foo_together.<locals>.<setcomp>rd   rû   r   )rŽ  rŒ  r	   rå   r  rè   )r'   rÄ   r•  r–  r·   Úremoval_valuer   rÔ  r    Ú&_generate_removed_altered_foo_togetherœ  s0   
ú
þ
ÿÿû€ðz<MigrationAutodetector._generate_removed_altered_foo_togetherc                 C   ó   |   tj¡ d S r#   )r×  r	   rä   r&   r   r   r    r‹   µ  ó   z>MigrationAutodetector.generate_removed_altered_unique_togetherc                 C   sV   |   |j¡D ]"\}}}}}| |¡}||kr(| j||dd|i|j|i¤Ž|d� qd S )Nrd   rû   r   )rŽ  rŒ  r  rè   )r'   rÄ   r•  r–  r™   r$   r·   rÖ  r   r   r    Ú_generate_altered_foo_together¸  s    
ú
ý€÷z4MigrationAutodetector._generate_altered_foo_togetherc                 C   rØ  r#   )rÚ  r	   rä   r&   r   r   r    r�   È  rÙ  z6MigrationAutodetector.generate_altered_unique_togetherc           	      C   ó�   | j  | j| j¡}t|ƒD ]8\}}| j ||f|¡}| jj||f }| j	j||f }|j
 d¡}|j
 d¡}||krE|  |tj||d�¡ qd S )NÚdb_table)rd   Útable)r�   Úunionrž   rŸ   r^   r›   rv   r1   r   r2   ru   rè   r	   ÚAlterModelTable)	r'   Úmodels_to_checkr™   r$   r¥   r¦   rD  Úold_db_table_nameÚnew_db_table_namer   r   r    r”   Ë  s*   ÿÿþþ€÷z/MigrationAutodetector.generate_altered_db_tablec           	      C   rÛ  )NÚdb_table_comment)rd   Útable_comment)r�   rÞ  rž   rŸ   r^   r›   rv   r1   r   r2   ru   rè   r	   ÚAlterModelTableComment)	r'   rà  r™   r$   r¥   r¦   rD  Úold_db_table_commentÚnew_db_table_commentr   r   r    rƒ   à  s*   ÿÿþþ€öz7MigrationAutodetector.generate_altered_db_table_commentc           	      C   s´   | j  | j| j| j| j@ | j| j@ ¡}t|ƒD ]@\}}| j	 
||f|¡}| jj||f }| jj||f }dd„ |j ¡ D ƒ}dd„ |j ¡ D ƒ}||krW|  |tj||d�¡ qdS )zÄ
        Work out if any non-schema-affecting options have changed and make an
        operation to represent them in state changes (in case Python code in
        migrations needs them).
        c                 S   ó    i | ]\}}|t jv r||“qS r   ©r   ÚALTER_OPTION_KEYSrG   r   r   r    rI     ó
    
þzBMigrationAutodetector.generate_altered_options.<locals>.<dictcomp>c                 S   rè  r   ré  rG   r   r   r    rI     rë  )rd   ru   N)r�   rÞ  rž   rŸ   rq   rr   ro   rt   r^   r›   rv   r1   r   r2   ru   rP   rè   r	   r   )	r'   rà  r™   r$   r¥   r¦   rD  Úold_optionsÚnew_optionsr   r   r    r�   ö  s8   

ú	ÿþþþþ€ïz.MigrationAutodetector.generate_altered_optionsc                 C   s²   t | jƒD ]Q\}}| j ||f|¡}| jj||f }| jj||f }|j d¡|j d¡krVg }|j d¡rE| t	|||jd t	j
jƒ¡ | j|tj||j d¡d�|d� qd S )Nrã   r  rû   )r^   r�   r›   rv   r1   r   r2   ru   ra   r   r!   r   rè   r	   râ   )r'   r™   r$   r¥   r¦   rD  r·   r   r   r    r�     sB   ÿÿ
þüÿ	ÿþø€êz<MigrationAutodetector.generate_altered_order_with_respect_toc                 C   sn   t | jƒD ]/\}}| j ||f|¡}| jj||f }| jj||f }|j|jkr4|  |t	j
||jd�¡ qd S )N)rd   r  )r^   r�   r›   rv   r1   r   r2   r  rè   r	   ÚAlterModelManagers)r'   r™   r$   r¥   r¦   rD  r   r   r    r‚   @  s    ÿþþ€ùz/MigrationAutodetector.generate_altered_managersc                    st  |  ¡ }i ‰ t| ¡ ƒD ]”\}}|sqd}|D ]}|d |kr#|} nq|du r@| j |¡s@|D ]}	|dfˆ ||	jf< q0||= q|du rGd}
n|  |d ¡pOdd }
t|ƒD ]I\}}	|dkrf|rf|	j 	|¡ d|
 g}|rs| 	|¡ n|dkr|s| 	d¡ n| 	|	 
¡ dd… ¡ d |¡}||fˆ ||	jf< |
d7 }
||	_qVq| ¡ D ]}|D ]}	‡ fd	d
„|	jD ƒ|	_q©q¥|S )zÁ
        Take a result from changes() and a MigrationGraph, and fix the names
        and dependencies of the changes so they extend the graph from the leaf
        nodes for each app.
        Nr   r¶   r   z%04ir¾   éd   rœ  c                    s   g | ]}ˆ   ||¡‘qS r   ©rv   r  ©Úname_mapr   r    rC     s    ÿz;MigrationAutodetector.arrange_for_graph.<locals>.<listcomp>)r¼   rM   rP   r3   Úask_initialrd   Úparse_numberÚ	enumerater·   ra   Úsuggest_nameÚjoinr¹   )r'   r=   r9   r<   Úleavesr™   r˜   Úapp_leafÚleafr×   Únext_numberÚiÚnew_name_partsrú   r   rñ  r    r7   P  sP   þ

ó

ÿÿz'MigrationAutodetector.arrange_for_graphc           
         s    i ‰ |  ¡ D ]\}}|D ]}|jD ]\}}ˆ  |tƒ ¡ |¡ qqqt|ƒ}d}	|	|kr@t|ƒ}	|j‡ fdd„|D ƒŽ  |	|ks,t|ƒD ]	}||vrM||= qD|S )a1  
        Take changes from arrange_for_graph() and set of app labels, and return
        a modified set of changes which trims out as many migrations that are
        not in app_labels as possible. Note that some other migrations may
        still be present as they may be required dependencies.
        Nc                    s   g | ]}ˆ   |d ¡‘qS )r   rð  )r-   r™   ©Úapp_dependenciesr   r    rC   —  r„  z7MigrationAutodetector._trim_to_apps.<locals>.<listcomp>)rP   r·   r¿   rn   rw   r½   rM   )
r'   r=   Ú
app_labelsr™   r˜   r×   rÉ  rd   Úrequired_appsÚold_required_appsr   rþ  r    r8   „  s(   ÿÿÿþ€z#MigrationAutodetector._trim_to_appsc                 C   s<   t  d|¡ }rt|d ƒS t  d|¡}|rt|d ƒS dS )uã   
        Given a migration name, try to extract a number from the beginning of
        it. For a squashed migration such as '0001_squashed_0004â€¦', return the
        second number. If no number is found, return None.
        z.*_squashed_(\d+)r   z^\d+r   N)ÚreÚsearchÚintÚmatch)Úclsrd   Úsquashed_matchr  r   r   r    rô  Ÿ  s   z"MigrationAutodetector.parse_numberr#   )NNN)NN)NF)9r   r   r   Ú__doc__r5   r=   r@   rg   r6   r{   r|   Ústaticmethodr®   r–   r•   r—   r»   rè   r÷   rz   r~   r€   r}   r   r„   r‰   r�   rP  rŒ   rl  rŽ   r…   r‘   rˆ   rŠ   r¯  r†   r’   r‡   r“   r   rV  rŸ  rŽ  r×  r‹   rÚ  r�   r”   rƒ   r�   r�   r‚   r7   r8   Úclassmethodrô  r   r   r   r    r,   *   sr    

&
j

x
T	D ^*_>%8{Y2
-/("
4r,   )!rQ   r  Úcollectionsr   r   Úenumr   Úgraphlibr   Ú	itertoolsr   Údjango.confr   Ú	django.dbr   Údjango.db.migrationsr	   Údjango.db.migrations.migrationr
   Ú&django.db.migrations.operations.modelsr   Údjango.db.migrations.optimizerr   Údjango.db.migrations.questionerr   Údjango.db.migrations.utilsr   r   r   Údjango.utils.functionalr   r   r,   r   r   r   r    Ú<module>   s&    
ÿ