Usunięcie ograniczenia (indeksu) z kolumny

12

Jak mogę zmodyfikować typ w tabeli z indeksem? Próbowałem zrobić kolumnę alter na pustej tabeli, aby zmodyfikować typ od daty do varchar (15) i dostałem błędy mówiące, że ma zależności od kolumny (która okazała się być indeksami).

Byłem w stanie łatwo obejść ten problem lokalnie, klikając prawym przyciskiem myszy indeks i wykonując skrypt na liście rozwijanej, ale muszę to rozpowszechnić na innych serwerach, na których nie będę mieć dostępu do nazwy indeksu.

Czy istnieje sposób, aby utworzyć skrypt, który usunie dowolny indeks, pozwól mi zmienić ten typ danych w kolumnie, a następnie odczytać indeks? Dzięki!

użytkownik1480
źródło

Odpowiedzi:

7

Aby uzyskać indeksy, możesz użyć widoku sys.indexes. Możesz dołączyć tę tabelę do sys.tables, sys.columns i sys.index_column, aby uzyskać informacje na temat tworzenia dynamicznego indeksu upuszczania. Możesz użyć tego prostego wyboru, aby wygenerować indeks upuszczenia. Możesz użyć klauzuli where do filtrowania tabel i kolumn. Jeśli chcesz zmienić Table1.Column1, musisz użyć tych nazw do filtrowania zaznaczenia, aby uzyskać prawidłową instrukcję usuwania

use [testdb]
go
declare @sqlDropIndex NVARCHAR(1000)

select @sqlDropIndex = 'DROP INDEX ' + idx.name + ' ON ' + tbl.name
from sys.indexes idx inner join 
        sys.tables tbl on idx.object_id = tbl.object_id inner join
        sys.index_columns idxCol on idx.index_id = idxCol.index_id inner join
        sys.columns col on idxCol.column_id = col.column_id
where idx.type <> 0 and
        tbl.name = 'MyTableName' and
        col.name = 'MyColumnName'
group by idx.name, tbl.name
order by idx.name desc

print @sqlDropIndex
--exec sp_executeSql @sqlDropIndex
go

Mam nadzieję, że to ci pomoże

Nico
źródło
3
dołączając, musisz wzbogacić instrukcje dołączania o idx.object_id = idxCol.object_id & idxCol.object_id = col.object_id i nie ma potrzeby grupowania.
Bax,
2

Aby zmienić dowolną kolumnę, najpierw musisz usunąć indeks lub inne ograniczenia zawierające tę kolumnę, a następnie ponownie utworzyć indeks / ograniczenie. Ale to zadanie musi wykonać DBA, ponieważ każde upuszczenie indeksu lub ograniczenie wpłynie z jednej strony na dane, o które pyta się - podczas gdy indeks jest upuszczany, a z drugiej strony nakłada blokadę na całą tabelę na czas ponownego indeksowania Utworzony. Musisz upewnić się, że użytkownicy będą świadomi tej małej lub dużej (w zależności od wielkości stołu) konserwacji. Powodzenia!

Jednak tworzenia indeksu można dokonać za pomocą opcji Online, która jest mniej blokująca.

yrushka
źródło
0

Jeśli upuścisz indeks jako pierwszy, nie będziesz w stanie odczytać go ponownie, chyba że indeks zostanie ponownie utworzony. Co możesz zrobić, aby wyłączyć wymuszanie ograniczenia.

ALTER TABLE name_of_the_table NOCHECK CONSTRAINT name_of_the_constraint;

Po uruchomieniu tego skryptu ograniczenie nie zostanie wymuszone, a dane można wprowadzać bez obawy o sprawdzenie ograniczeń. Możesz ponownie zmienić tabelę, aby ponownie włączyć ograniczenia.

ALTER TABLE name_of_the_table CHECK CONSTRAINT name_of_the_constraint;

Wszelkie wcześniejsze naruszenia nie zostaną sprawdzone ani poprawione, ale wszelkie wpisy po wymuszeniu ograniczenia zostaną sprawdzone.

StanleyJohns
źródło
-2

W odpowiedzi Niko występują 2 błędy (brak 2 warunków object_id). I nie trzeba group by:

SELECT  @sql = 'DROP INDEX ' + idx.name + ' ON ' + tbl.name
FROM    sys.indexes             idx 
INNER JOIN sys.tables           tbl     ON idx.object_id = tbl.object_id 
INNER JOIN sys.index_columns    idxCol  ON idx.index_id = idxCol.index_id   AND idx.object_id = idxCol.object_id 
INNER JOIN sys.columns          col     ON idxCol.column_id = col.column_id AND  idxCol.object_id = col.object_id
WHERE   idx.type <> 0 
AND     tbl.name = 'file_transfer_log' 
AND     col.name = 'tender_id';
Val Starovoitov
źródło
1
Zobacz Dlaczego powinienem zarejestrować swoje konto? w FAQ wymiany stosów.
Paul White 9