Why isn't my Auto Increment working in SQL Server 2008? - sql

This is my table creation:
create table Movie
(
MovieID int NOT NULL IDENTITY (1,1) PRIMARY KEY,
MovieName varchar(40) NOT NULL UNIQUE,
CurrentStock int NOT NULL,
GenreID int NOT NULL,
RatingID int NOT NULL,
Max_Inventory int NOT NULL,
Platforms char(5) NOT NULL,
Discontinued bit,
DiscontinuedDate Date
);
create table Inventory
(
InventoryID int NOT NULL IDENTITY (1,1) PRIMARY KEY,
MovieID int Not NULL,
CurrentStock int NOT NULL,
Max_Inventory int NOT NULL
);
Stored procedures:
ALTER PROCEDURE [dbo].[InsInventory]
(#CurrentStock int,
#ChangeStock int)
as
begin
insert into Inventory(Max_Inventory, CurrentStock)
Values (#ChangeStock, #CurrentStock)
select SCOPE_IDENTITY();
END
ALTER PROCEDURE [dbo].[InsMovie]
(#GenreID int,
#RatingID int,
#Platform varchar(5),
#MovieName varchar(40)
)
AS
BEGIN
Insert into Movie (RatingID, MovieName, Platforms, GenreID)
Values (#RatingID, #MovieName, #Platform, #GenreID)
select SCOPE_IDENTITY();
SET NOCOUNT ON;
END
Foreign key:
ALTER Table Inventory
ADD CONSTRAINT fk_Inventory_Movie
FOREIGN KEY (MovieID) REFERENCES Movie(MovieID)
ALTER TABLE Movie
ADD CONSTRAINT fk_Movie_RatingLookUp
FOREIGN KEY (RatingID) REFERENCES RatingLookUp(RatingID)
ALTER TABLE Movie
ADD CONSTRAINT fk_Movie_GenreLookUp
FOREIGN KEY (GenreID) REFERENCES GenreLookUp (GenreID)
When I run my code I keep getting the error in Visual Studio
MovieID cannot be null
but it should be when I insert a row. I also made sure to manually check to see if SQL Server had the IsIdentity set, which it is. So please help a confused programmer out.

You shouldn't insert NULL as a primary key to make it generate a value, you should just don't insert that value at all by not listing it among the fields to insert. As a sample;
INSERT INTO Movie (moviename, currentstock, genreid, ratingid, max_inventory, platforms)
VALUES ('name1', 1, 1, 1, 1, '1');
A simple working sample with your exact table creation.

Below statement is your problem. your table def shows MovieID not null. but in below statement you didn't provide that.
insert into Inventory(Max_Inventory, CurrentStock)
Values (#ChangeStock, #CurrentStock)
here is what you need to do.. first you need to retrieve Movie id which will be return from executing InsMovie sproc. than you need to use that Movie Id as a prameter to InsInvetory sproc call.
according to your table def movie id is required. also for Movie table you missed two column values that i have added which are required as well.
Please see blow updated stored procedures.
ALTER PROCEDURE [dbo].[InsInventory]
(
#CurrentStock int,
#ChangeStock int,
#MovieID int
)
as
begin
insert into Inventory(MovieID, Max_Inventory,CurrentStock)
Values (#MovieID, #ChangeStock, #CurrentStock)
select SCOPE_IDENTITY();
END
ALTER PROCEDURE [dbo].[InsMovie]
(
#GenreID int,
#RatingID int,
#Platform varchar(5),
#MovieName varchar(40),
#CurrentStock int,
#max_inventory int
)
AS
BEGIN
Insert into Movie (CurrentStock, max_inventory, RatingID, MovieName, Platforms,GenreID)
Values(#CurrentStock, #max_inventory, #RatingID,#MovieName, #Platform, #GenreID)
select SCOPE_IDENTITY();
SET NOCOUNT ON;
END

Related

INSERT INTO many-to-many table with existing rows

I'm currently merging two databases to one and facing a problem with a many-to-many table.
I got the following SQL structure:
CREATE TABLE [dbo].[Module] (
ModuleID INT IDENTITY(1,1) PRIMARY KEY NOT NULL,
Name VARCHAR(50) NOT NULL
)
CREATE TABLE [dbo].[Message] (
MessageID INT IDENTITY(1,1) PRIMARY KEY NOT NULL,
Name VARCHAR(50) NOT NULL,
Size INT NOT NULL
)
CREATE TABLE [dbo].[Bind] (
ModuleID INT FOREIGN KEY REFERENCES Module(ModuleID) NOT NULL,
MessageID INT FOREIGN KEY REFERENCES Message(Message) NOT NULL
)
and was already able to insert the values for the tables Module and Message.
Now i struggle with inserting the existing connections (e.g. ModuleID = 1 with MessageID = 5,1,7,9,6) to the table Bind.
I would like to achieve this with a sql script.
Thank you in advance.
Mady
you can use this query :
INSERT INTO Module (Name) VALUES ('Name 1');
SET #ModuleID = LAST_INSERT_ID();
INSERT INTO Message (Name,Size) VALUES ('Message 1',50);
SET #MessageID = LAST_INSERT_ID();
INSERT INTO Bind (MessageID,ModuleID) VALUES(#ModuleID, #MessageID);

How to get the auto-generated primary key after insertion in stored procedure?

My SQL Server table:
[dbo].[Rep] (
[rep_ID] INT IDENTITY (300, 1) NOT NULL,
[Restaurant_ID] INT NULL,
[Fname] VARCHAR (50) NOT NULL,
[Lname] VARCHAR (50) NOT NULL,
CONSTRAINT [PK_Rep_ID] PRIMARY KEY CLUSTERED ([rep_ID] ASC),
CONSTRAINT [FK_Restaurant_ID] FOREIGN KEY ([Restaurant_ID]) REFERENCES [dbo].[Restaurants] ([ID])
);
I want to create a stored procedure that return the auto generated key for the inserted record.
My current stored procedure:
CREATE PROCEDURE [dbo].[createRepAcc]
#first varchar(50),
#last varchar(50)
AS
INSERT INTO Rep([Fname], [Lname])
OUTPUT inserted.rep_ID
VALUES (#first, #last);
It's able to insert into the table but only return 1 instead of the primary key generated.
What am I doing wrong?
You can use scope_identity() to get the last generated id. For your case here is a detailed worksheet
/* creating a simple table with identity column */
CREATE TABLE dbo.a(identity_column INT IDENTITY(300,1), x CHAR(1));
/* Procedure that inserts values and returns generated output*/
CREATE PROCEDURE [dbo].[ap]
#x char(1),
#id int output
AS
INSERT INTO a(x) VALUES (#x);
select #id = SCOPE_IDENTITY();
/* This is how the procedure could be called */
declare #ident int -- declare a variable to receive output
execute dbo.ap #x='b', #id=#ident output -- execute or call the procedure
select #ident -- select or print the genereated id

How i can change and run sql file into mssql

I have my database in sqlite .I exported sql file from sqlite manager. Now on executing that file into Microsoft SQL Server 2012 it is giving error on following lines.
DROP TABLE
IF EXISTS "Admin";
CREATE TABLE "AdvancePayments" (
"Id" INT PRIMARY KEY AUTOINCREMENT NOT NULL UNIQUE,
"date" VARCHAR,
"Name" VARCHAR,
"Amount" INT,
"Remarks" VARCHAR);
INSERT INTO "AdvancePayments"
VALUES (
1,
'11/22/2013',
'wqqw',
21,
'fgdsr');
CREATE TABLE "DVouchers" (
"DVid" INT PRIMARY KEY NOT NULL,
"vdate" VARCHAR DEFAULT(NULL),
"Vehiclenum" VARCHAR,
"Coupen" BOOL,
"Saleperson" VARCHAR,
"DVnumber" INT,
"Ares" VARCHAR,
"Ctitle" VARCHAR,
"remarks" VARCHAR,
"mEntry" BOOL,
"Cust_Id" INT,
FOREIGN KEY (Cust_Id) REFERENCES Customer_New(Cust_Id));
What is correct syntax for mssql?
You should write it as:
--DROP TABLE IF EXISTS Admin;
--query to drop a table
IF EXISTS (SELECT * FROM sys.objects WHERE object_id = OBJECT_ID(N'[dbo].[TableName]') AND type in (N'U'))
DROP TABLE [dbo].[TableName]
GO
CREATE TABLE [AdvancePayments]
(
[Id] INT IDENTITY(1,1) PRIMARY KEY NOT NULL ,--The MS SQL Server uses the IDENTITY keyword to perform an auto-increment feature
[date] VARCHAR(10),-- best practice is to use datetime datatype to store date feilds.
[Name] VARCHAR(100),
[Amount] INT,
[Remarks] VARCHAR(1000)
);
INSERT INTO AdvancePayments
VALUES (
--1,-- you cannot give an explicit value to identity column untill IDENTITY_INSERT is ON. So comment this.
'11/22/2013',
'wqqw',
21,
'fgdsr');
CREATE TABLE [DVouchers] (
[DVid] INT PRIMARY KEY NOT NULL,
[vdate] VARCHAR(20) DEFAULT(NULL),
[Vehiclenum] VARCHAR(100),
[Coupen] BIT,-- Bit is the datatype used for Boolean values.
[Saleperson] VARCHAR(100),
[DVnumber] INT,
[Ares] VARCHAR(100),
[Ctitle] VARCHAR(100),
[remarks] VARCHAR(100),
[mEntry] BIT,
[Cust_Id] INT,
FOREIGN KEY (Cust_Id) REFERENCES Customer_New(Cust_Id)
);
Note: In MS SQL default length of varchar datatype is 1. so you will have to specify length to each
varchar variable.
TSQL:
IF NOT OBJECT_ID('dbo.TableToDrop') IS NULL
BEGIN
DROP TABLE dbo.TableToDrop
END;
// change dbo. to your schema if necessary

Multilingual database design

I'm trying to design a database schema for a multilingual application. I have so far found a sample from this address. http://fczaja.blogspot.com/2010/08/multilanguage-database-design.html
But I haven't understood this sample. Should I insert Id value on app_product first? How can I know that these values are true for ProductId on app_product_translation?
CREATE TABLE ref_language (
Code Char(2)NOT NULL,
Name Varchar(20) NOT NULL,
PRIMARY KEY (Code)
);
CREATE TABLE app_product (
Id Int IDENTITY NOT NULL,
PRIMARY KEY (Id)
);
CREATE TABLE app_product_translation (
ProductId Int NOT NULL,
LanguageCode Char(2) NOT NULL,
Description Text NOT NULL,
FOREIGN KEY (ProductId) REFERENCES app_product(Id),
FOREIGN KEY (LanguageCode) REFERENCES ref_language(Code)
);
It looks like SQLServer code, proceeding on that assumption.
Yes you must insert the app_product first. But you cannot insert the id column's value. It is assigned automatically, because it is an identity column.
Two things you can check out...to find the identity column's value after inserting.
The OUTPUT clause of the INSERT statement. It can return any values that are inserted, not just the identity column.
The ##Identity variable. (by far more traditional and popular)
declare #lastid int
insert into x values (1,2,3)
set #lastid = ##identity
insert into y values (#lastid, a, b, c)

SQL Server add primary key

I have a table that needs to be given a new primary key, as my predecesor used a varchar(8) row as the primary key, and we are having problems with it now. I know how to add the primary key, but am not sure of the correct way to add this new primary key to other tables that have the foreign key. Here is what I have:
users table:
old_user_id varchar(8)
...
...
new_user_id int
orders table:
order_id int
...
...
old_user_fk varchar(8)
new_user_fk int(11)
I need to get the same results whether I join the tables on users.old_user_id=orders.old_user_fk or users.new_user_id=orders.new_user_fk. Any help is appreciated.
What is int(11)? SQL Server only has tinyint, smallint, int and bigint
I would suggest you add the new columns to all the tables then update the values so that they match....run a couple of queries to make sure it all works. drop the PK and FK constraints and add new PK and FK constraints using the new columns
of course I would back up all these tables just in case
select * into backup_ orders from orders
This way you always have that data in case you need to roll back
Replace your varchar with int, do not keep duplicates in the same table.
Write some TSQL similar this code I used recently:
BEGIN TRANSACTION
-- temp tables to hold data
DECLARE #HeaderTemp table
(vid varchar(8),
[Name] varchar (50) )
DECLARE #SecondaryTemp table
(vid_fk varchar(8),
[Value] varchar (50) )
-- store table data
INSERT INTO #HeaderTemp
SELECT * FROM [Header]
INSERT INTO #SecondaryTemp
SELECT * FROM [Secondary]
-- empty data from tables
DELETE FROM [Secondary]
DELETE FROM [Header]
-- drop constraints
ALTER TABLE [SECONDARY] DROP CONSTRAINT [FK_SECONDARY_HEADER]
ALTER TABLE [dbo].[HEADER] DROP CONSTRAINT [PK_HEADER]
-- convert varchar to int
ALTER TABLE [SECONDARY] ALTER COLUMN VID_FK INT NOT NULL
ALTER TABLE [HEADER] ALTER COLUMN VID INT NOT NULL
-- re-create constraints
ALTER TABLE [dbo].[HEADER] ADD CONSTRAINT [PK_HEADER] PRIMARY KEY CLUSTERED
(
[vid] ASC
)
ALTER TABLE [dbo].[SECONDARY] WITH CHECK ADD CONSTRAINT [FK_SECONDARY_HEADER]
FOREIGN KEY([vid_fk]) REFERENCES [dbo].[HEADER] ([vid])
-- put data back
INSERT INTO [Header]
SELECT * FROM #HeaderTemp
INSERT INTO [Secondary]
SELECT * FROM #SecondaryTemp
COMMIT TRANSACTION