3
gQ                 @   s|   d dl 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 G d
d deZdS )    N)Decimal)Apps)NotSupportedError)BaseDatabaseSchemaEditor)	Statement)strip_quotes)UniqueConstraint)atomicc                   s   e Zd ZdZdZdZdZdZ fddZ fdd	Z	d
d Z
d&ddZd' fdd	Zd( fdd	Zd)ddZd* fdd	Zdd Zdd Zd+ddZdd Z fd d!Z fd"d#Zd$d% Z  ZS ),DatabaseSchemaEditorzDROP TABLE %(table)sNzEREFERENCES %(to_table)s (%(to_column)s) DEFERRABLE INITIALLY DEFERREDz7CREATE UNIQUE INDEX %(name)s ON %(table)s (%(columns)s)zDROP INDEX %(name)sc                s   | j j stdt j S )NzSQLite schema editor cannot be used while foreign key constraint checks are enabled. Make sure to disable them before entering a transaction.atomic() context because SQLite does not support disabling them in the middle of a multi-statement transaction.)
connectiondisable_constraint_checkingr   super	__enter__)self)	__class__ _/var/www/tester-filtro-web/env/lib/python3.6/site-packages/django/db/backends/sqlite3/schema.pyr      s    
zDatabaseSchemaEditor.__enter__c                s(   | j j  t j||| | j j  d S )N)r   Zcheck_constraintsr   __exit__enable_constraint_checking)r   exc_type	exc_value	traceback)r   r   r   r   "   s    
zDatabaseSchemaEditor.__exit__c             C   s   ydd l }|j|}W n( tk
r*   Y n |jk
r>   Y nX t|trVtt|S t|tt	tfrnt|S t|trd|j
dd S |d krdS t|tttfrd|j  S td|t|f d S )Nr   z'%s''z''ZNULLzX'%s'z*Cannot quote parameter value %r of type %s)sqlite3ZadaptImportErrorZProgrammingError
isinstanceboolstrintr   floatreplacebytes	bytearray
memoryviewhex
ValueErrortype)r   valuer   r   r   r   quote_value'   s$    

z DatabaseSchemaEditor.quote_valueFc       
      C   s   | j j z}xr| j jj|D ]`}|r0|j|kr0q| j jj||j}x8|j D ],}|d \}}	||krL|dkst|	|krLdS qLW qW W dQ R X dS )a  
        Return whether or not the provided table name is referenced by another
        one. If `column_name` is specified, only references pointing to that
        column are considered. If `ignore_self` is True, self-referential
        constraints are ignored.
        Zforeign_keyNTF)r   cursorZintrospectionZget_table_listnameZ_get_foreign_key_constraintsvalues)
r   
table_nameZcolumn_nameignore_selfr)   Zother_tableconstraints
constraintZconstraint_tableZconstraint_columnr   r   r   _is_referenced_by_fk_constraintC   s    z4DatabaseSchemaEditor._is_referenced_by_fk_constraintTc                sh   | j jj rT|rT| j|rT| j jr.td| | j j  t j||| | j j	  nt j||| d S )NzRenaming the %r table while in a transaction is not supported on SQLite < 3.26 because it would break referential integrity. Try adding `atomic = False` to the Migration class.)
r   features!supports_atomic_references_renamer0   in_atomic_blockr   r   r   alter_db_tabler   )r   modelZold_db_tableZnew_db_tabledisable_constraints)r   r   r   r4   V   s    
z#DatabaseSchemaEditor.alter_db_tablec                s`  | j ||sd S |j}|jj}|j \}}|j|koN| jjj oN| j||ddrH| jj	rnt
d|jj|f t| jj t j||||d | jj |}	|	jdj d }
|	jd d| }|j d	 }|| }|| }|	jd
||f |	jd|
d	   |	jd |	jd W d Q R X W d Q R X | jj }	|	jd W d Q R X nt j||||d d S )NT)r-   zRenaming the %r.%r column while in a transaction is not supported on SQLite < 3.26 because it would break referential integrity. Try adding `atomic = False` to the Migration class.)strictzPRAGMA schema_versionr   zPRAGMA writable_schema = 1z REFERENCES "%s" ("%%s")    z3UPDATE sqlite_master SET sql = replace(sql, %s, %s)zPRAGMA schema_version = %dzPRAGMA writable_schema = 0zPRAGMA integrity_checkZVACUUM)Z_field_should_be_alteredr*   _metadb_tableZget_attname_columnr   r1   r2   r0   r3   r   r	   aliasr   alter_fieldr)   executeZfetchone)r   r5   	old_field	new_fieldr7   Zold_field_namer,   _Zold_column_namer)   Zschema_versionZreferences_templateZnew_column_namesearchreplacement)r   r   r   r<   e   s8    


z DatabaseSchemaEditor.alter_fieldc                s^  fddfddj jD }fddj jD }i d}t|dds`|rt|d	 ddrx<t|j D ],\}}	|	jrnd|	_|	}|	jrn||= ||	j= qnW |r|||j< |j	 r|j
rЈjj|||j< |rb|\}
}|j|
jd |j|
jd |||j< |
jrD|j rDd
j|
jjj|d }|||j< nj|
j||j< |j|
j<  r| j= | j=  j	r jjj jrj jjS t }fddj jD }fddj jD }j j} r fdd|D }tj j}tj|}j jj j|||||d}tdf |}||d< j|d< tj jj| tj|}j jdt j j |||||d}tdf |}||d< j|d< tdj j j|}j!| j"dj|j jdj#fdd|D dj#|j$ jj jf  jdd j%||j jj jdd xj&D ]}j"| q4W g _&|rZd|_dS )a|  
        Shortcut to transform a model from old_model into new_model

        This follows the correct procedure to perform non-rename or column
        addition operations based on SQLite's documentation

        https://www.sqlite.org/lang_altertable.html#caution

        The essential steps are:
          1. Create a table with the updated definition called "new__app_model"
          2. Copy the data from the existing "app_model" table to the new table
          3. Drop the "app_model" table
          4. Rename the "new__app_model" table to "app_model"
          5. Restore any index of the previous "app_model" table.
        c                s   | j o| jj kS )N)Zis_relationremote_fieldr5   )f)r5   r   r   is_self_referential   s    z?DatabaseSchemaEditor._remake_table.<locals>.is_self_referentialc                s$   i | ]} |r|j  n||jqS r   )cloner*   ).0rD   )rE   r   r   
<dictcomp>   s   z6DatabaseSchemaEditor._remake_table.<locals>.<dictcomp>c                s   i | ]} j |j|jqS r   )
quote_namecolumn)rG   rD   )r   r   r   rH      s    Nprimary_keyFr8   zcoalesce(%(col)s, %(default)s))coldefaultc                s   g | ]} fd d|D qS )c                s   g | ]} j ||qS r   )get)rG   n)rename_mappingr   r   
<listcomp>   s    zADatabaseSchemaEditor._remake_table.<locals>.<listcomp>.<listcomp>r   )rG   unique)rP   r   r   rQ      s   z6DatabaseSchemaEditor._remake_table.<locals>.<listcomp>c                s   g | ]} fd d|D qS )c                s   g | ]} j ||qS r   )rN   )rG   rO   )rP   r   r   rQ      s    zADatabaseSchemaEditor._remake_table.<locals>.<listcomp>.<listcomp>r   )rG   index)rP   r   r   rQ      s   c                s   g | ]} j |jkr|qS r   )r*   fields)rG   rS   )delete_fieldr   r   rQ      s    )	app_labelr:   unique_togetherindex_togetherindexesr.   appsZMeta
__module__znew__%szNew%sz%INSERT INTO %s (%s) SELECT %s FROM %sz, c             3   s   | ]} j |V  qd S )N)rI   )rG   x)r   r   r   	<genexpr>  s    z5DatabaseSchemaEditor._remake_table.<locals>.<genexpr>)handle_autom2m)r6   T)'r9   Zlocal_concrete_fieldsgetattrlistitemsrK   auto_createdrJ   r*   many_to_manyZconcreter(   Zeffective_defaultpopnullrI   rC   throughdelete_modelr   rW   rX   rY   r.   copydeepcopyrV   r:   r&   r[   Zobject_name	__bases__r   create_modelr=   joinr+   r4   deferred_sql)r   r5   create_fieldrU   r<   bodymappingZrestore_pk_fieldr*   fieldr>   r?   Zcase_sqlrZ   rW   rX   rY   r.   Z	body_copyZmeta_contentsmetaZ	new_modelsqlr   )rU   rE   r5   rP   r   r   _remake_table   s    










z"DatabaseSchemaEditor._remake_tablec                sl   |rt  j| nV| j| jd| j|jji  x6t| jD ](}t	|t
r<|j|jjr<| jj| q<W d S )Ntable)r   rg   r=   sql_delete_tablerI   r9   r:   r`   rm   r   r   Zreferences_tableremove)r   r5   r^   rs   )r   r   r   rg   5  s    z!DatabaseSchemaEditor.delete_modelc             C   s2   |j r |jjjjr | j|jjS | j||d dS )z
        Create a field on a model. Usually involves adding a column, but may
        involve adding a table instead (for M2M fields).
        )rn   N)rc   rC   rf   r9   rb   rk   rt   )r   r5   rq   r   r   r   	add_fieldB  s    zDatabaseSchemaEditor.add_fieldc             C   sN   |j r"|jjjjrJ| j|jj n(|j| jdd dkr<dS | j||d dS )z
        Remove a field from a model. Usually involves deleting a column,
        but for M2Ms may involve deleting a table.
        )r   r&   N)rU   )	rc   rC   rf   r9   rb   rg   Zdb_parametersr   rt   )r   r5   rq   r   r   r   remove_fieldL  s    z!DatabaseSchemaEditor.remove_fieldc	             C   sH  | j jjrb|j|jkrb| j||| j||krb|jr:|jpD|joD|j rb| j| j|j	j
|||S | j|||fd |jo||krDt }	|jj	}
xV|
jD ]L}|j|krq|js|j|jkr|	j|j q|jr|jj	jr|	j|j qW |jr*x6|
jD ],}|j|krq|jjj	jr|	j|jj qW x|	D ]}| j| q0W dS )z3Perform a "physical" (non-ManyToMany) field update.)r<   N)r   r1   Zcan_alter_table_rename_columnrJ   Z
column_sqlrC   Zdb_constraintr=   Z_rename_field_sqlr9   r:   rt   rR   setr5   Zrelated_objectsrelated_modelrc   
field_namer*   addrK   rf   rb   )r   r5   r>   r?   Zold_typenew_typeZold_db_paramsZnew_db_paramsr7   Zrelated_modelsoptsrC   rc   r{   r   r   r   _alter_field^  s4    


z!DatabaseSchemaEditor._alter_fieldc             C   s   |j jjj|j jjjkrR| j|j j|j jjj|j |j jjj|j fd dS | j|j j | jd| j	|j jjjdj
d|j |j gdj
d|j |j g| j	|j jjjf  | j|j j dS )z*Alter M2Ms to repoint their to= endpoints.)r<   Nz%INSERT INTO %s (%s) SELECT %s FROM %sz, id)rC   rf   r9   r:   rt   	get_fieldZm2m_reverse_field_namerk   r=   rI   rl   Zm2m_column_nameZm2m_reverse_namerg   )r   r5   r>   r?   r7   r   r   r   _alter_many_to_many  s&    

z(DatabaseSchemaEditor._alter_many_to_manyc                s.   t |tr |jr t j|| n
| j| d S )N)r   r   	conditionr   add_constraintrt   )r   r5   r/   )r   r   r   r     s    z#DatabaseSchemaEditor.add_constraintc                s.   t |tr |jr t j|| n
| j| d S )N)r   r   r   r   remove_constraintrt   )r   r5   r/   )r   r   r   r     s    z&DatabaseSchemaEditor.remove_constraintc             C   s   d| S )Nz	 COLLATE r   )r   Z	collationr   r   r   _collate_sql  s    z!DatabaseSchemaEditor._collate_sql)NF)T)F)NNN)T)F)__name__r[   __qualname__rv   Zsql_create_fkZsql_create_inline_fkZsql_create_uniqueZsql_delete_uniquer   r   r(   r0   r4   r<   rt   rg   rx   ry   r   r   r   r   r   __classcell__r   r   )r   r   r
      s*   
)
 (

##r
   )rh   decimalr   Zdjango.apps.registryr   Z	django.dbr   Zdjango.db.backends.base.schemar   Z!django.db.backends.ddl_referencesr   Zdjango.db.backends.utilsr   Zdjango.db.modelsr   Zdjango.db.transactionr	   r
   r   r   r   r   <module>   s   