diff --git a/oopgrade/oopgrade.py b/oopgrade/oopgrade.py index 1035bbb..f76c106 100644 --- a/oopgrade/oopgrade.py +++ b/oopgrade/oopgrade.py @@ -305,6 +305,74 @@ def column_exists(cr, table, column): return cr.fetchone()[0] == 1 +def create_index(cursor, table, index_name, columns): + ''' + :param cursor: + :param table: + :param index_name: :type str Limit 63 cropped characters without spaces. Giscesdata replaced to "gd" + :param columns :type list + :return: + ''' + + # CREATE INDEX ON FKs + indexname = index_name.lower() + indexname = indexname.replace('giscedata', 'gd')[:63] + + cursor.execute( + """ + select t.relname as table_name, i.relname as index_name, + am.amname as typeof, + array_agg(a.attname) as column_names + from + pg_class t, pg_class i, pg_index ix, + pg_attribute a, pg_am am + where + t.oid = ix.indrelid + and i.oid = ix.indexrelid + and a.attrelid = t.oid + and a.attnum = ANY(ix.indkey) + and i.relam = am.oid + and t.relkind = 'r' + and t.relname = %s + group by + t.relname, i.relname, am.amname + """, + (table, ) + ) + res = cursor.dictfetchall() + found_idx_name = False + found_columns = False + for x in res: + if indexname == x['index_name']: + found_idx_name = True + index_columns = x['column_names'] + if len(columns) == len(index_columns): + equal_order = True + for cols in zip(columns, index_columns): + if cols[0] != cols[1]: + equal_order = False + if equal_order: + found_columns = True + columns_text = ','.join(columns) + if not found_idx_name and not found_columns: + logger.info( + 'create index on ' + 'columns {0} in table {1}'.format( + columns_text, table + ) + ) + cursor.execute( + 'CREATE INDEX "%s" ON "%s" (%s)' % ( + indexname, table, columns_text) + ) + else: + logger.warn( + 'SKIP create index, because detected index ' + 'for columns {0} in table' + ' {1}'.format(columns_text, table) + ) + + def change_column_type(cursor, column_spec): """ :param cr: Cursor diff --git a/spec/data_migration_spec.py b/spec/data_migration_spec.py index 16f4c0d..fbc9551 100644 --- a/spec/data_migration_spec.py +++ b/spec/data_migration_spec.py @@ -160,4 +160,42 @@ def callback(): *expected_sql )) + with description('Create index'): + with it(''): + result = [ + { + 'table_name': 'giscedata_polissa', + 'index_name': 'giscedata_polissa_name_index', 'typeof': 'btree', + 'column_names': 'name' + }, + { + 'table_name': 'giscedata_polissa', + 'index_name': 'giscedata_polissa_name_unic', 'typeof': 'btree', + 'column_names': 'name' + }, + { + 'table_name': 'giscedata_polissa', + 'index_name': 'giscedata_polissa_ordre_carta_index', 'typeof': 'btree', + 'column_names': 'ordre_carta'}, + { + 'table_name': 'giscedata_polissa', + 'index_name': 'giscedata_polissa_pagador_index', 'typeof': 'btree', + 'column_names': 'pagador' + }, + { + 'table_name': 'giscedata_polissa', + 'index_name': 'giscedata_polissa_pkey', 'typeof': 'btree', + 'column_names': 'id' + }, + { + 'table_name': 'giscedata_polissa', + 'index_name': 'giscedata_polissa_zona_carta_index', 'typeof': 'btree', + 'column_names': 'zona_carta' + }, + { + 'table_name': 'giscedata_polissa', + 'index_name': 'idx_giscedata_polissa_dadbc', 'typeof': 'btree', + 'column_names': 'cups, data_alta, data_baixa' + } + ]