2013-08-01 2 views
1

Quelle est la meilleure méthode (faible impact/faible risque) pour modifier un champ de clé primaire de SMALLINT à INT? Le champ est configuré pour utiliser "Incrément d'identité" pour l'auto-incrémentation.Modifier le champ Auto-Increment, Primary Key de SMALLINT à INT dans SQL Server

Je suis en commençant par l'instruction SQL suivante:

ALTER TABLE category_types ALTER COLUMN id INT NOT NULL; 

Cependant, il génère l'erreur suivante:

ALTER TABLE ALTER COLUMN id failed because one or more objects access this column.

Que faut-il? Dois-je laisser tomber les clés puis les recréer? Cela aura-t-il un impact sur l'auto-incrémentation?

Remarque: la table n'a pas trop de lignes, donc les performances de la solution ne sont pas critiques.

+0

Salut, je suis pas d'avoir une expertise dans le serveur SQL, mais pensez que vous avez oublié la « identité » à la fin de l'instruction ALTER. – Babblo

Répondre

1

Ceci est une sortie du studio de gestion de serveur sql mais devrait être utile. Cela implique de créer une table temporaire, puis de copier les données existantes dans la nouvelle table. Suppression de la table d'origine et renommer la table temporaire. Si la table était vide, elle ne le ferait pas et pourrait simplement modifier la table d'origine. SET IDENTITY_INSERT [table] ON/OFF vous permet de définir la colonne d'identité lors de l'insertion.

/* To prevent any potential data loss issues, you should review this script in detail before running it outside the context of the database designer.*/ 
BEGIN TRANSACTION 
SET QUOTED_IDENTIFIER ON 
SET ARITHABORT ON 
SET NUMERIC_ROUNDABORT OFF 
SET CONCAT_NULL_YIELDS_NULL ON 
SET ANSI_NULLS ON 
SET ANSI_PADDING ON 
SET ANSI_WARNINGS ON 
COMMIT 
BEGIN TRANSACTION 
GO 
CREATE TABLE dbo.Tmp_category_types 
    (
    id int NOT NULL IDENTITY (1, 1), 
    ) ON [PRIMARY] 
GO 
ALTER TABLE dbo.Tmp_category_types SET (LOCK_ESCALATION = TABLE) 
GO 
SET IDENTITY_INSERT dbo.Tmp_category_types ON 
GO 
IF EXISTS(SELECT * FROM dbo.category_types) 
    EXEC('INSERT INTO dbo.Tmp_category_types (id, x) 
     SELECT CONVERT(int, id), x FROM dbo.category_types WITH (HOLDLOCK TABLOCKX)') 
GO 
SET IDENTITY_INSERT dbo.Tmp_category_types OFF 
GO 
DROP TABLE dbo.category_types 
GO 
EXECUTE sp_rename N'dbo.Tmp_category_types', N'category_types', 'OBJECT' 
GO 
ALTER TABLE dbo.category_types ADD CONSTRAINT 
    PK_category_types PRIMARY KEY CLUSTERED 
    (
    id 
    ) WITH(STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY] 

GO 
COMMIT 
0

Outre la mise en IDENTITY_INSERT off, vous devez Délierrelations (clés primaires, clés étrangères) avant de changer de types de données. Ensuite, vous devez lien à nouveau.

Par exemple:

-- Change from smallint to int 
SET IDENTITY_INSERT category_types OFF 
alter table category_types drop CONSTRAINT CategoryTypesPK 
alter table category_types alter column id int 
alter table category_types add CONSTRAINT CategoryTypesPK PRIMARY KEY (id) 
SET IDENTITY_INSERT category_types ON 
2

Je sais que c'est un ancien poste, mais juste au cas où quelqu'un trébuche dessus: jciberta a donné une réponse avec une légère erreur. il faut lire:

- Changement de smallint à int

SET IDENTITY_INSERT type_categorie SUR

type_categorie alter table drop constraint CategoryTypes

type_categorie alter table modifier id colonne int

alter table category_types add CONSTRAINT CatégorieTypesPK PRIMARY KEY (id)

SET IDENTITY_INSERT type_categorie OFF

Questions connexes