Django

Code

Changeset 2346

Show
Ignore:
Timestamp:
02/18/06 15:26:28 (2 years ago)
Author:
adrian
Message:

Fixed #1286 -- Improved 'inspectdb' so that it introspects primary_key=True and unique=True for MySQL. Thanks, gandalf@owca.info

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • django/trunk/AUTHORS

    r2341 r2346  
    5252    Jeremy Dunck <http://dunck.us/> 
    5353    Clint Ecker 
     54    gandalf@owca.info 
    5455    Baishampayan Ghose 
    5556    Espen Grindhaug <http://grindhaug.org/> 
  • django/trunk/django/core/db/backends/ado_mssql.py

    r2325 r2346  
    119119    raise NotImplementedError 
    120120 
     121def get_indexes(cursor, table_name): 
     122    raise NotImplementedError 
     123 
    121124OPERATOR_MAPPING = { 
    122125    'exact': '= %s', 
  • django/trunk/django/core/db/backends/mysql.py

    r2325 r2346  
    135135def get_relations(cursor, table_name): 
    136136    raise NotImplementedError 
     137 
     138def get_indexes(cursor, table_name): 
     139    "Returns a dict of indexes for given table" 
     140    cursor.execute("SHOW INDEX FROM %s" % DatabaseWrapper().quote_name(table_name)) 
     141    indexes = {} 
     142    for row in cursor.fetchall(): 
     143        indexes[row[4]] = {'keyname': row[2], 'unique': not bool(row[1])} 
     144    return indexes 
    137145 
    138146OPERATOR_MAPPING = { 
  • django/trunk/django/core/db/backends/postgresql.py

    r2325 r2346  
    126126            continue 
    127127    return relations 
     128 
     129def get_indexes(cursor, table_name): 
     130    raise NotImplementedError 
    128131 
    129132# Register these custom typecasts, because Django expects dates/times to be 
  • django/trunk/django/core/db/backends/sqlite3.py

    r2325 r2346  
    133133 
    134134def get_relations(cursor, table_name): 
     135    raise NotImplementedError 
     136 
     137def get_indexes(cursor, table_name): 
    135138    raise NotImplementedError 
    136139 
  • django/trunk/django/core/db/__init__.py

    r1484 r2346  
    3838get_table_description = dbmod.get_table_description 
    3939get_relations = dbmod.get_relations 
     40get_indexes = dbmod.get_indexes 
    4041OPERATOR_MAPPING = dbmod.OPERATOR_MAPPING 
    4142DATA_TYPES = dbmod.DATA_TYPES 
  • django/trunk/django/core/management.py

    r2328 r2346  
    596596        except NotImplementedError: 
    597597            relations = {} 
     598        try: 
     599            indexes = db.get_indexes(cursor, table_name) 
     600        except NotImplementedError: 
     601            indexes = {} 
    598602        for i, row in enumerate(db.get_table_description(cursor, table_name)): 
    599             column_name = row[0] 
     603            att_name = row[0] 
    600604            comment_notes = [] # Holds Field notes, to be displayed in a Python comment. 
    601605            extra_params = {}  # Holds Field parameters such as 'db_column'. 
    602606 
    603             if keyword.iskeyword(column_name): 
    604                 extra_params['db_column'] = column_name 
    605                 column_name += '_field' 
     607            if keyword.iskeyword(att_name): 
     608                extra_params['db_column'] = att_name 
     609                att_name += '_field' 
    606610                comment_notes.append('Field renamed because it was a Python reserved word.') 
    607611 
     
    609613                rel_to = relations[i][1] == table_name and "'self'" or table2model(relations[i][1]) 
    610614                field_type = 'ForeignKey(%s' % rel_to 
    611                 if column_name.endswith('_id'): 
    612                     column_name = column_name[:-3] 
     615                if att_name.endswith('_id'): 
     616                    att_name = att_name[:-3] 
    613617                else: 
    614                     extra_params['db_column'] = column_name 
     618                    extra_params['db_column'] = att_name 
    615619            else: 
    616620                try: 
     
    626630                    extra_params.update(new_params) 
    627631 
     632                # Add maxlength for all CharFields. 
    628633                if field_type == 'CharField' and row[3]: 
    629634                    extra_params['maxlength'] = row[3] 
    630635 
     636                # Add primary_key and unique, if necessary. 
     637                column_name = extra_params.get('db_column', att_name) 
     638                if column_name in indexes: 
     639                    if indexes[column_name]['keyname'] == 'PRIMARY': 
     640                        extra_params['primary_key'] = True 
     641                    elif indexes[column_name]['unique']: 
     642                        extra_params['unique'] = True 
     643 
    631644                field_type += '(' 
    632645 
    633             field_desc = '%s = meta.%s' % (column_name, field_type) 
     646            # Don't output 'id = meta.AutoField(primary_key=True)', because 
     647            # that's assumed if it doesn't exist. 
     648            if att_name == 'id' and field_type == 'AutoField(' and extra_params == {'primary_key': True}: 
     649                continue 
     650 
     651            field_desc = '%s = meta.%s' % (att_name, field_type) 
    634652            if extra_params: 
    635653                if not field_desc.endswith('('): 
  • django/trunk/docs/django-admin.txt

    r2271 r2346  
    113113This feature is meant as a shortcut, not as definitive model generation. After 
    114114you run it, you'll want to look over the generated models yourself to make 
    115 customizations. In particular, you'll need to do this: 
    116  
    117     * Rearrange models' order, so that models that refer to other models are 
    118       ordered properly. 
    119     * Add ``primary_key=True`` to one field in each model. The ``inspectdb`` 
    120       doesn't yet introspect primary keys. 
     115customizations. In particular, you'll need to rearrange models' order, so that 
     116models that refer to other models are ordered properly. 
     117 
     118If you're using Django 0.90 or 0.91, you'll need to add ``primary_key=True`` to 
     119one field in each model. In the Django development version, primary keys are 
     120automatically introspected for MySQL, and Django puts in the 
     121``primary_key=True`` where needed. 
    121122 
    122123``inspectdb`` works with PostgreSQL, MySQL and SQLite. Foreign-key detection