2010-04-28 10 views
6

Ho due tabelle con 10-20 milioni di righe che dispongono di chiavi primarie GUID e di 12 tabelle correlate tramite chiave esterna. Le tabelle di base hanno 10-20 indici ciascuno.Approccio per la modifica della chiave primaria da GUID a BigInt nelle tabelle relative a SQL Server

Stiamo passando dal GUID alle chiavi primarie BigInt. Mi chiedo se qualcuno ha qualche suggerimento su un approccio. Proprio ora questo è l'approccio che sto meditando:

  1. Eliminare tutti gli indici e le fkeys su tutte le tabelle coinvolte.
  2. Add colonna 'NewPrimaryKey' ad ogni tavolo
  3. Effettuare l'identità chiave sulle due tabelle di base
  4. Script il cambiamento dei dati "tabella di aggiornamento x, impostare NewPrimaryKey = y dove OldPrimaryKey = z
  5. Rinominare il PrimaryKey originale a 'oldprimarykey'
  6. Rinominare il 'NewPrimaryKey' colonna 'PrimaryKey'
  7. script indietro tutti gli indici ei tasti fkeys

Vi sembra come un buon approccio? Qualcuno sa di uno strumento o script che potrebbe aiutare con questo?

TD: Modificato per ulteriori informazioni. Vedere questo post del blog che risolve un approccio quando il GUID è il primario: http://www.sqlmag.com/blogs/sql-server-questions-answered/sql-server-questions-answered/tabid/1977/entryid/12749/Default.aspx

+0

Quale percorso hai finito? Oltre a quello che hai detto, l'applicazione dovrà essere sicuro di sapere che PrimaryKey è ora il tuo nuovo tipo di dati e non Guid. – user420667

risposta

0

Si suona certamente come questa strategia avrebbe funzionato - cadere i vincoli, cambiando la colonna da sotto di loro (tipo cambia, il nome rimane lo stesso), e quindi ricreare i vincoli è abbastanza elegante.

L'obiettivo è di eliminare definitivamente le colonne GUID? Se è così, non sarà effettivamente recuperare lo spazio a meno che i tavoli sono copiati o ricostruiti, quindi forse le seguenti regolazioni:

...
4.Script il cambiamento dei dati "tabella di aggiornamento x, impostare NewPrimaryKey = y dove oldPrimaryKey = z
5. goccia il PrimaryKey originale per 'oldprimarykey'
6.Rename colonna 'NewPrimaryKey' 'PrimaryKey'
7.Script indietro tutti gli indici e fkeys (edificio cluster indici "ricostruisce" tabelle)
8. Per tutte le tabelle che non dispongono di indici cluster, fare qualcosa per assicurarsi che vengano ricostruiti e il loro spazio sia reclamato (tale build e quindi rilasciare un indice cluster)

Inutile dire che testarlo su un box di sviluppo prima di eseguire Produzione!

+0

Per retrocompatibile con alcune vecchie e-mail con collegamenti, è necessario mantenere il vecchio ID nelle due tabelle di base, quindi se un vecchio link entra possiamo localizzarlo, altrimenti, sulle relative tabelle possiamo rilasciare la vecchia colonna – BoomTownTech

3

L'approccio è come lo farei.

Hai davvero bisogno di bigint? un normale 4 byte int andrà a 2 miliardi (2.147.483.647).

int, bigint, smallint, and tinyint

+0

Possiamo raggiungerlo in 10 anni o giù di lì .... è semplicemente un problema di spazio o un int fornisce prestazioni decisamente migliori sugli indici? – BoomTownTech

+3

16 byte per guid (uniqueidentifier), o 8 per bigint, o solo 4 byte per normale int. Questo non è solo lo spazio su disco, ma anche la memoria cache. Inoltre, avrai più chiavi su una pagina (ricerca più veloce) e ogni indice include il PK, quindi più piccolo è meglio è. –

0

Vorrei anche aggiungere:

Assicurarsi di avere un buon backup corrente prima di iniziare. Cambiare il server per l'esecuzione in modalità utente singolo (informare prima gli utenti di un periodo di indisponibilità). Non vuoi che gli utenti provino a inserire dati mentre sta succedendo.