Django

Code

Changeset 5787

Show
Ignore:
Timestamp:
08/02/07 16:17:23 (1 year ago)
Author:
danderson
Message:

schema-evolution:
added sqlite3 unit tests
greatly expanded the number of evolutions supported by the sqlite3 backend
changed all get_<evolution_type> calls to return lists of strings
fixed sqlite3 get_indexes introspection

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • django/branches/schema-evolution/django/core/management.py

    r5785 r5787  
    570570            col_type = data_types[data_type] 
    571571            if col_type is not None: 
    572                 output.append( backend.get_add_column_sql( db_table, f.column, style.SQL_COLTYPE(col_type % rel_field.__dict__), f.null, f.unique, f.primary_key ) ) 
     572                output.extend( backend.get_add_column_sql( db_table, f.column, style.SQL_COLTYPE(col_type % rel_field.__dict__), f.null, f.unique, f.primary_key ) ) 
    573573    return output 
    574574 
     
    581581        return [], None 
    582582    if klass._meta.aka in table_list: 
    583         return [ backend.get_change_table_name_sql( klass._meta.db_table, klass._meta.aka) ], klass._meta.aka 
     583        return backend.get_change_table_name_sql( klass._meta.db_table, klass._meta.aka), klass._meta.aka 
    584584    elif len(set(klass._meta.aka) & set(table_list))==1: 
    585         return [ backend.get_change_table_name_sql( klass._meta.db_table, klass._meta.aka[0]) ], klass._meta.aka[0] 
     585        return backend.get_change_table_name_sql( klass._meta.db_table, klass._meta.aka[0]), klass._meta.aka[0] 
    586586    else: 
    587587        return [], None 
     
    609609            col_type = data_types[data_type] 
    610610            if col_type is not None: 
    611                 field_output = [] 
    612611                col_def = style.SQL_COLTYPE(col_type % rel_field.__dict__) +' '+ style.SQL_KEYWORD('%sNULL' % (not f.null and 'NOT ' or '')) 
    613612                if f.unique: 
     
    615614                if f.primary_key: 
    616615                    col_def += style.SQL_KEYWORD(' PRIMARY KEY') 
    617                 field_output.append( backend.get_change_column_name_sql( klass._meta.db_table, introspection.get_indexes(cursor,db_table), backend.quote_name(old_col), backend.quote_name(f.column), col_def ) ) 
    618                 output.append(' '.join(field_output)) 
     616                output.extend( backend.get_change_column_name_sql( klass._meta.db_table, introspection.get_indexes(cursor,db_table), old_col, f.column, col_def ) ) 
    619617    return output 
    620618     
     
    667665#                if f.primary_key: 
    668666#                    col_def += ' '+ style.SQL_KEYWORD('PRIMARY KEY') 
    669                 output.append( backend.get_change_column_def_sql( db_table, cf, col_type_def, f.null, f.unique, f.primary_key ) ) 
     667                output.extend( backend.get_change_column_def_sql( db_table, cf, col_type_def, f.null, f.unique, f.primary_key ) ) 
    670668                    #print db_table, cf, f.maxlength, introspection.get_known_column_flags(cursor, db_table, cf) 
    671669    return output 
  • django/branches/schema-evolution/django/db/backends/mysql/base.py

    r5785 r5787  
    245245 
    246246def get_change_table_name_sql( table_name, old_table_name ): 
    247     return 'ALTER TABLE '+ quote_name(old_table_name) +' RENAME TO '+ quote_name(table_name) + ';' 
     247    return ['ALTER TABLE '+ quote_name(old_table_name) +' RENAME TO '+ quote_name(table_name) + ';'] 
    248248 
    249249def get_change_column_name_sql( table_name, indexes, old_col_name, new_col_name, col_def ): 
     
    255255    output = [] 
    256256    output.append( 'ALTER TABLE '+ quote_name(table_name) +' CHANGE COLUMN '+ quote_name(old_col_name) +' '+ quote_name(new_col_name) +' '+ col_def + ';' ) 
    257     return '\n'.join(output) 
     257    return output 
    258258 
    259259def get_change_column_def_sql( table_name, col_name, col_type, null, unique, primary_key ): 
     
    265265        col_def += ' '+ 'PRIMARY KEY' 
    266266    output.append( 'ALTER TABLE '+ quote_name(table_name) +' MODIFY COLUMN '+ quote_name(col_name) +' '+ col_def + ';' ) 
    267     return '\n'.join(output) 
     267    return output 
    268268 
    269269def get_add_column_sql( table_name, col_name, col_type, null, unique, primary_key  ): 
     
    281281        field_output.append(('PRIMARY KEY')) 
    282282    output.append(' '.join(field_output) + ';') 
    283     return '\n'.join(output) 
     283    return output 
    284284 
    285285def get_drop_column_sql( table_name, col_name ): 
  • django/branches/schema-evolution/django/db/backends/postgresql/base.py

    r5785 r5787  
    287287    output = [] 
    288288    output.append('ALTER TABLE '+ quote_name(old_table_name) +' RENAME TO '+ quote_name(table_name) + ';') 
    289     return '\n'.join(output) 
     289    return output 
    290290 
    291291def get_change_column_name_sql( table_name, indexes, old_col_name, new_col_name, col_def ): 
     
    296296    output = [] 
    297297    output.append( 'ALTER TABLE '+ quote_name(table_name) +' RENAME COLUMN '+ quote_name(old_col_name) +' TO '+ quote_name(new_col_name) +';' ) 
    298     return '\n'.join(output) 
     298    return output 
    299299 
    300300def get_change_column_def_sql( table_name, col_name, col_type, null, unique, primary_key ): 
     
    309309        output.append( 'ALTER TABLE '+ quote_name(table_name) +' ADD CONSTRAINT '+ table_name +'_'+ col_name +'_unique_constraint UNIQUE('+ col_name +');' ) 
    310310     
    311     return '\n'.join(output) 
     311    return output 
    312312 
    313313def get_add_column_sql( table_name, col_name, col_type, null, unique, primary_key  ): 
     
    318318    if unique: 
    319319        output.append( 'ALTER TABLE '+ quote_name(table_name) +' ADD CONSTRAINT '+ table_name +'_'+ col_name +'_unique_constraint UNIQUE('+ col_name +');' ) 
    320     return '\n'.join(output) 
     320    return output 
    321321     
    322322def get_drop_column_sql( table_name, col_name ): 
  • django/branches/schema-evolution/django/db/backends/sqlite3/base.py

    r5785 r5787  
    218218 
    219219def get_change_table_name_sql( table_name, old_table_name ): 
    220     return 'ALTER TABLE '+ quote_name(old_table_name) +' RENAME TO '+ quote_name(table_name) + ';' 
     220    return ['ALTER TABLE '+ quote_name(old_table_name) +' RENAME TO '+ quote_name(table_name) + ';'] 
    221221 
    222222def get_change_column_name_sql( table_name, indexes, old_col_name, new_col_name, col_def ): 
    223223    # sqlite doesn't support column renames, so we fake it 
    224     # TODO: only supports a single primary key so far 
    225     pk_name = None 
    226     for key in indexes.keys(): 
    227         if indexes[key]['primary_key']: pk_name = key 
    228     output = [] 
    229     output.append( 'ALTER TABLE '+ quote_name(table_name) +' ADD COLUMN '+ quote_name(new_col_name) +' '+ col_def + ';' ) 
    230     output.append( 'UPDATE '+ quote_name(table_name) +' SET '+ new_col_name +' = '+ old_col_name +' WHERE '+ pk_name +'=(select '+ pk_name +' from '+ table_name +');' ) 
    231     output.append( '-- FYI: sqlite does not support deleting columns, so  '+ quote_name(old_col_name) +' remains as cruft' ) 
    232     return '\n'.join(output) 
     224    model = get_model_from_table_name(table_name) 
     225    output = [] 
     226    output.append( '-- FYI: sqlite does not support renaming columns, so we create a new '+ quote_name(table_name) +' and delete the old  (ie, this could take a while)' ) 
     227 
     228    tmp_table_name = table_name + '_1337_TMP' # unlikely to produce a namespace conflict 
     229    output.extend( get_change_table_name_sql( tmp_table_name, table_name ) ) 
     230    output.extend( management._get_sql_model_create(model, set())[0] ) 
     231 
     232    old_cols = [] 
     233    for f in model._meta.fields: 
     234        if f.column != new_col_name: 
     235            old_cols.append( quote_name(f.column) ) 
     236        else:  
     237            old_cols.append( quote_name(old_col_name) ) 
     238 
     239    output.append( 'INSERT INTO '+ quote_name(table_name) +' SELECT '+ ','.join(old_cols) +' FROM '+ quote_name(tmp_table_name) +';' ) 
     240    output.append( 'DROP TABLE '+ quote_name(tmp_table_name) +';' ) 
     241 
     242    return output 
    233243 
    234244def get_change_column_def_sql( table_name, col_name, col_type, null, unique, primary_key ): 
    235245    # sqlite doesn't support column modifications, so we fake it 
     246 
     247    model = get_model_from_table_name(table_name) 
     248    if not model: return ['-- model not found'] 
     249    output = [] 
     250    output.append( '-- FYI: sqlite does not support changing columns, so we create a new '+ quote_name(table_name) +' and delete the old  (ie, this could take a while)' ) 
     251 
     252    tmp_table_name = table_name + '_1337_TMP' # unlikely to produce a namespace conflict 
     253    output.extend( get_change_table_name_sql( tmp_table_name, table_name ) ) 
     254    output.extend( management._get_sql_model_create(model, set())[0] ) 
     255 
     256    old_cols = [] 
     257    for f in model._meta.fields: 
     258        old_cols.append( quote_name(f.column) ) 
     259 
     260    output.append( 'INSERT INTO '+ quote_name(table_name) +' SELECT '+ ','.join(old_cols) +' FROM '+ quote_name(tmp_table_name) +';' ) 
     261    output.append( 'DROP TABLE '+ quote_name(tmp_table_name) +';' ) 
     262 
     263    return output 
     264 
     265 
     266 
     267 
     268 
     269 
     270 
     271 
     272 
     273 
     274 
    236275    output = [] 
    237276    col_def = col_type +' '+ ('%sNULL' % (not null and 'NOT ' or '')) 
     
    242281    # TODO: fake via renaming the table, building a new one and deleting the old 
    243282    output.append('-- sqlite does not support column modifications '+ quote_name(table_name) +'.'+ quote_name(col_name) +' to '+ col_def) 
    244     return '\n'.join(output) 
     283    return output 
    245284     
    246285def get_add_column_sql( table_name, col_name, col_type, null, unique, primary_key  ): 
     
    258297        field_output.append(('PRIMARY KEY')) 
    259298    output.append(' '.join(field_output) + ';') 
    260     return '\n'.join(output) 
     299    return output 
    261300 
    262301def get_drop_column_sql( table_name, col_name ): 
     
    265304    output.append( '-- FYI: sqlite does not support deleting columns, so we create a new '+ quote_name(col_name) +' and delete the old  (ie, this could take a while)' ) 
    266305    tmp_table_name = table_name + '_1337_TMP' # unlikely to produce a namespace conflict 
    267     output.append( get_change_table_name_sql( tmp_table_name, table_name ) ) 
     306    output.extend( get_change_table_name_sql( tmp_table_name, table_name ) ) 
    268307    output.extend( management._get_sql_model_create(model, set())[0] ) 
    269308    new_cols = [] 
  • django/branches/schema-evolution/django/db/backends/sqlite3/introspection.py

    r5785 r5787  
    2727    """ 
    2828    indexes = {} 
    29     for info in _table_info(cursor, table_name): 
    30         indexes[info['name']] = {'primary_key': info['pk'] != 0, 
    31                                  'unique': False} 
    3229    cursor.execute('PRAGMA index_list(%s)' % quote_name(table_name)) 
    3330    # seq, name, unique 
     
    3734        cursor.execute('PRAGMA index_info(%s)' % quote_name(index)) 
    3835        info = cursor.fetchall() 
    39         # Skip indexes across multiple fields 
    40         if len(info) != 1: 
    41             continue 
    42         name = info[0][2] # seqno, cid, name 
    43         indexes[name]['unique'] = True 
     36        for x in info: 
     37            name = x[2] # seqno, cid, name 
     38            cursor.execute('PRAGMA table_info(%s)' % quote_name(table_name)) 
     39            for row in cursor.fetchall(): 
     40                if row[1]==name: 
     41                    indexes[name] = {'primary_key': False, 'unique': False} 
     42                    if row[2]=='integer': 
     43                        indexes[name]['primary_key'] = True 
     44                    else: 
     45                        indexes[name]['unique'] = True 
    4446    return indexes 
    4547 
  • django/branches/schema-evolution/tests/modeltests/schema_evolution/models.py

    r5785 r5787  
    4545>>> sql = backend.get_drop_column_sql( 'schema_evolution_person', 'gender' ) 
    4646>>> print sql 
    47 ALTER TABLE `schema_evolution_person` DROP COLUMN `gender`; 
    48 >>> cursor.execute(sql
     47['ALTER TABLE `schema_evolution_person` DROP COLUMN `gender`;'] 
     48>>> for s in sql: cursor.execute(s
    49490L 
    5050>>> management.get_sql_evolution(app) 
     
    59590L 
    6060>>> management.get_sql_evolution(app) 
    61 ['-- warning: as the following may cause data loss, it/they must be run manually', u'-- ALTER TABLE `schema_evolution_person` DROP COLUMN `gender_nothere`;', '-- end warning'] 
     61['-- warning: the following may cause data loss', u'ALTER TABLE `schema_evolution_person` DROP COLUMN `gender_nothere`;', '-- end warning'] 
    6262 
    6363# reset the db 
     
    104104 
    105105# delete a column, so it looks like we've recently added a field 
    106 >>> cursor.execute( backend.get_drop_column_sql( 'schema_evolution_person', 'gender' )
    107 >>> management.get_sql_evolution(app) 
    108 ['ALTER TABLE "schema_evolution_person" ADD COLUMN "gender" varchar(1);\\nALTER TABLE "schema_evolution_person" ALTER COLUMN "gender" SET NOT NULL;'] 
     106>>> for sql in backend.get_drop_column_sql( 'schema_evolution_person', 'gender' ): cursor.execute(sql
     107>>> management.get_sql_evolution(app) 
     108['ALTER TABLE "schema_evolution_person" ADD COLUMN "gender" varchar(1);', 'ALTER TABLE "schema_evolution_person" ALTER COLUMN "gender" SET NOT NULL;'] 
    109109 
    110110# reset the db 
     
    112112 
    113113# add a column, so it looks like we've recently deleted a field 
    114 >>> cursor.execute( backend.get_add_column_sql( 'schema_evolution_person', 'gender_nothere', 'varchar(1)', True, False, False )
    115 >>> management.get_sql_evolution(app) 
    116 ['-- warning: as the following may cause data loss, it/they must be run manually', u'-- ALTER TABLE "schema_evolution_person" DROP COLUMN "gender_nothere";', '-- end warning'] 
     114>>> for sql in backend.get_add_column_sql( 'schema_evolution_person', 'gender_nothere', 'varchar(1)', True, False, False ): cursor.execute(sql
     115>>> management.get_sql_evolution(app) 
     116['-- warning: the following may cause data loss', u'ALTER TABLE "schema_evolution_person" DROP COLUMN "gender_nothere";', '-- end warning'] 
    117117 
    118118# reset the db 
     
    120120 
    121121# rename column, so it looks like we've recently renamed a field 
    122 >>> cursor.execute( backend.get_change_column_name_sql( 'schema_evolution_person', {}, 'gender2', 'gender_old', 'varchar(1)' )
     122>>> for sql in backend.get_change_column_name_sql( 'schema_evolution_person', {}, 'gender2', 'gender_old', 'varchar(1)' ): cursor.execute(sql
    123123>>> management.get_sql_evolution(app) 
    124124['ALTER TABLE "schema_evolution_person" RENAME COLUMN "gender_old" TO "gender2";'] 
     
    128128 
    129129# rename table, so it looks like we've recently renamed a model 
    130 >>> cursor.execute( backend.get_change_table_name_sql( 'schema_evolution_personold', 'schema_evolution_person' )
     130>>> for sql in backend.get_change_table_name_sql( 'schema_evolution_personold', 'schema_evolution_person' ): cursor.execute(sql
    131131>>> management.get_sql_evolution(app) 
    132132['ALTER TABLE "schema_evolution_personold" RENAME TO "schema_evolution_person";'] 
     
    136136 
    137137# change column flags, so it looks like we've recently changed a column flag 
    138 >>> cursor.execute( backend.get_change_column_def_sql( 'schema_evolution_person', 'name', 'varchar(10)', True, False, False )
    139 >>> management.get_sql_evolution(app) 
    140 ['ALTER TABLE "schema_evolution_person" ADD COLUMN "name_tmp" varchar(20);\\nUPDATE "schema_evolution_person" SET "name_tmp" = "name";\\nALTER TABLE "schema_evolution_person" DROP COLUMN "name";\\nALTER TABLE "schema_evolution_person" RENAME COLUMN "name_tmp" TO "name";\\nALTER TABLE "schema_evolution_person" ALTER COLUMN "name" SET NOT NULL;'] 
     138>>> for sql in backend.get_change_column_def_sql( 'schema_evolution_person', 'name', 'varchar(10)', True, False, False ): cursor.execute(sql
     139>>> management.get_sql_evolution(app) 
     140['ALTER TABLE "schema_evolution_person" ADD COLUMN "name_tmp" varchar(20);', 'UPDATE "schema_evolution_person" SET "name_tmp" = "name";', 'ALTER TABLE "schema_evolution_person" DROP COLUMN "name";', 'ALTER TABLE "schema_evolution_person" RENAME COLUMN "name_tmp" TO "name";', 'ALTER TABLE "schema_evolution_person" ALTER COLUMN "name" SET NOT NULL;'] 
    141141 
    142142""" 
     
    172172>>> cursor.execute( 'CREATE TABLE "schema_evolution_person" ( "id" integer NOT NULL UNIQUE PRIMARY KEY, "name" varchar(20) NOT NULL, "gender" varchar(1) NOT NULL, "gender2" varchar(1) NOT NULL, "gender_new" varchar(1) NOT NULL );' ).__class__ 
    173173<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
    174 >>> management.get_sql_evolution(app) 
     174>>> cursor.execute( 'insert into "schema_evolution_person" values (1,2,3,4,5);' ).__class__ 
     175<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     176>>> sql = management.get_sql_evolution(app) 
     177>>> print sql 
    175178['-- warning: the following may cause data loss', u'-- FYI: sqlite does not support deleting columns, so we create a new "gender_new" and delete the old  (ie, this could take a while)', 'ALTER TABLE "schema_evolution_person" RENAME TO "schema_evolution_person_1337_TMP";', 'CREATE TABLE "schema_evolution_person" (\\n    "id" integer NOT NULL UNIQUE PRIMARY KEY,\\n    "name" varchar(20) NOT NULL,\\n    "gender" varchar(1) NOT NULL,\\n    "gender2" varchar(1) NOT NULL\\n)\\n;', 'INSERT INTO "schema_evolution_person" SELECT "id","name","gender","gender2" FROM "schema_evolution_person_1337_TMP";', 'DROP TABLE "schema_evolution_person_1337_TMP";', '-- end warning'] 
     179>>> for s in sql: cursor.execute(s).__class__ 
     180<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     181<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     182<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     183<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     184<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     185<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     186<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     187>>> cursor.execute('select * from "schema_evolution_person";').__class__ 
     188<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     189>>> cursor.fetchall()[0] 
     190(1, u'2', u'3', u'4') 
    176191 
    177192# reset the db 
     
    181196<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
    182197 
    183 """ 
    184  
    185 crap = """ 
    186  
    187198# rename column, so it looks like we've recently renamed a field 
    188 >>> cursor.execute( backend.get_change_column_name_sql( 'schema_evolution_person', {}, 'gender2', 'gender_old', 'varchar(1)' ) ) 
    189 >>> management.get_sql_evolution(app) 
    190 ['ALTER TABLE "schema_evolution_person" RENAME COLUMN "gender_old" TO "gender2";'] 
    191  
    192 # reset the db 
    193 >>> cursor.execute('DROP TABLE schema_evolution_person;'); cursor.execute(create_table_sql[0]) 
     199>>> cursor.execute('DROP TABLE "schema_evolution_person"').__class__ 
     200<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     201>>> cursor.execute('').__class__ 
     202<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     203>>> cursor.execute('CREATE TABLE "schema_evolution_person" ("id" integer NOT NULL UNIQUE PRIMARY KEY, "name" varchar(20) NOT NULL, "gender" varchar(1) NOT NULL, "gender_old" varchar(1) NOT NULL );').__class__ 
     204<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     205>>> cursor.execute( 'insert into "schema_evolution_person" values (1,2,3,4);' ).__class__ 
     206<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     207>>> sql = management.get_sql_evolution(app) 
     208>>> print sql 
     209['-- FYI: sqlite does not support renaming columns, so we create a new "schema_evolution_person" and delete the old  (ie, this could take a while)', 'ALTER TABLE "schema_evolution_person" RENAME TO "schema_evolution_person_1337_TMP";', 'CREATE TABLE "schema_evolution_person" (\\n    "id" integer NOT NULL UNIQUE PRIMARY KEY,\\n    "name" varchar(20) NOT NULL,\\n    "gender" varchar(1) NOT NULL,\\n    "gender2" varchar(1) NOT NULL\\n)\\n;', 'INSERT INTO "schema_evolution_person" SELECT "id","name","gender","gender_old" FROM "schema_evolution_person_1337_TMP";', 'DROP TABLE "schema_evolution_person_1337_TMP";'] 
     210>>> for s in sql: cursor.execute(s).__class__ 
     211<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     212<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     213<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     214<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     215<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     216>>> cursor.execute('select * from "schema_evolution_person";').__class__ 
     217<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     218>>> cursor.fetchall()[0] 
     219(1, u'2', u'3', u'4') 
     220 
     221# reset the db 
     222>>> cursor.execute('DROP TABLE schema_evolution_person;').__class__ 
     223<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     224>>> cursor.execute(create_table_sql[0]).__class__ 
     225<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
    194226 
    195227# rename table, so it looks like we've recently renamed a model 
    196 >>> cursor.execute( backend.get_change_table_name_sql( 'schema_evolution_personold', 'schema_evolution_person' ) ) 
     228>>> for sql in backend.get_change_table_name_sql( 'schema_evolution_personold', 'schema_evolution_person' ): cursor.execute(sql).__class__ 
     229<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
    197230>>> management.get_sql_evolution(app) 
    198231['ALTER TABLE "schema_evolution_personold" RENAME TO "schema_evolution_person";'] 
    199232 
    200233# reset the db 
    201 >>> cursor.execute(create_table_sql[0]) 
     234>>> cursor.execute('DROP TABLE schema_evolution_personold;').__class__ 
     235<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     236>>> cursor.execute(create_table_sql[0]).__class__ 
     237<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
    202238 
    203239# change column flags, so it looks like we've recently changed a column flag 
    204 >>> cursor.execute( backend.get_change_column_def_sql( 'schema_evolution_person', 'name', 'varchar(10)', True, False, False ) ) 
    205 >>> management.get_sql_evolution(app) 
    206 ['ALTER TABLE "schema_evolution_person" ADD COLUMN "name_tmp" varchar(20);\\nUPDATE "schema_evolution_person" SET "name_tmp" = "name";\\nALTER TABLE "schema_evolution_person" DROP COLUMN "name";\\nALTER TABLE "schema_evolution_person" RENAME COLUMN "name_tmp" TO "name";\\nALTER TABLE "schema_evolution_person" ALTER COLUMN "name" SET NOT NULL;'] 
    207  
    208 """ 
    209  
     240>>> cursor.execute('DROP TABLE "schema_evolution_person";').__class__ 
     241<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     242>>> cursor.execute('CREATE TABLE "schema_evolution_person" ( "id" integer NOT NULL UNIQUE PRIMARY KEY, "name" varchar(20) NOT NULL, "gender" varchar(1) NOT NULL, "gender2" varchar(1) NULL);').__class__ 
     243<class 'django.db.backends.sqlite3.base.SQLiteCursorWrapper'> 
     244>>> management.get_sql_evolution(app) 
     245['-- FYI: sqlite does not support changing columns, so we create a new "schema_evolution_person" and delete the old  (ie, this could take a while)', 'ALTER TABLE "schema_evolution_person" RENAME TO "schema_evolution_person_1337_TMP";', 'CREATE TABLE "schema_evolution_person" (\\n    "id" integer NOT NULL UNIQUE PRIMARY KEY,\\n    "name" varchar(20) NOT NULL,\\n    "gender" varchar(1) NOT NULL,\\n    "gender2" varchar(1) NOT NULL\\n)\\n;', 'INSERT INTO "schema_evolution_person" SELECT "id","name","gender","gender2" FROM "schema_evolution_person_1337_TMP";', 'DROP TABLE "schema_evolution_person_1337_TMP";'] 
     246""" 
     247