views:

224

answers:

4

I have created a database where I use uniqueidentifier as the primary key. I'm trying to run a parametrized query that in the end looks like this. (insert into someTable (uniqueID) Values('76c14693-5475-4224-ba94-7d30c919ac59') (uniqueID is my PK). This insert statement executes without issues when I run it in SQL Server Management Studio, however, it fails when I try to run it from my code.

Error: Cannot insert explicit value for identity column in table 'someTable' when IDENTITY_INSERT is set to OFF.

I have looked this up and there are a lot of suggestions on turning ON the IDENTITY_INSERT but they all use stored procedures. I need to be able to do this using a parametrized query. Or I need a way to get the newly created guid in the database. This seems like something everyone would need at some point. Are there any simple solutions?

PS. I need the ID because I need to add records to other tables using that ID.

EDIT:

Here is the Structure of the table in question

CREATE TABLE [dbo].[someTable]
( 
        [NewsID] [uniqueidentifier] NOT NULL CONSTRAINT [DF_someTable_NewsID] DEFAULT (newid()), 
        [ShortTitle] [nvarchar](255) COLLATE SQL_Latin1_General_CP1_CI_AS NULL, 
        [DateCreated] [datetime] NULL CONSTRAINT [DF_someTable_DateCreated] DEFAULT (getdate()), 
        CONSTRAINT [PK_cmc_News_1] PRIMARY KEY CLUSTERED ( 
            [NewsID] ASC )WITH (PAD_INDEX = OFF, IGNORE_DUP_KEY = OFF
        ) ON [PRIMARY] 
) ON [PRIMARY]

Thanks in advance!

Thanks to you guys my issue is now resolved. I was connecting to the wrong database that unfortunately had the same table name but used an INT Identity field. So, that is why I was getting that error. Sorry everyone. I just wasted your time here, but I would not have figured this out if it wasn't for some of the posts. If it helps you feel any better I just wasted my whole morning on this stupid issue. Thanks again!

A: 

IN the first place GUIDs area a horrible choice for primary keys.

If you are using them however, you should not also have the same filed defined as an identity field. Please post your table structure code and we can help you redefine it correctly.

HLGEM
If you do not use CLUSTERED PK's it is not so much terrible choice. However performance penalties are another story.
Vnuk
And performance is critical to databases so unless you need replication, never consdier using a GUID for a PK.
HLGEM
I tried to post but couldn't because I don't have 10 points.
zoran
A PK is basically nothing different than a unique constraint, so by saying never consider a GUID for a PK is really no different than saying never consider a GUID for a unique constraint/index - I'm assuming you wouldn't say that it never a good idea to index a GUID, since there are many scenarios where doing so makes sense. Like anything, it always depends on the requirements, scenario, etc. Are there times when it doesn't make sense to do so? Absolutely. Are the just as many times when it does? Absolutely. Very speculative to make such a broad statement
chadhoc
wrong chadhoc, a PK is very differnt from a unique index. It is used in joins to the FK tables. This affects performance a great deal. Using GUIDs is just a poor practice for pks more often than it isn't. I'm speaking from 30+ years of database development and having had to use or develop against hundreds of databases. I've never yet seen a database that used a GUID where the performance was acceptable once there were a fair amount of records. A expert can consider using a GUID knowing the possible impact, no one else should.
HLGEM
So what is the the best choice for a PK? I will have to merge data at some point for multiple customers. I do not want to have records from two customers that have the same PK.
zoran
HLGEM, it's only used for joins to FKs if you actually define FKs to the parent table's PK - there is absolutely nothing stopping you from defining FKs from a child table to a non-PK column with a unique constraint defined, it's simply semantic differences.
chadhoc
And as for using a GUID with acceptable performance with a fair amount of records, I'm actually looking at a table with over 75 billion records that includes 3 guids, 2 of which are uniquely indexed...again, it's not a simple cut and dry statement that should be made blanket, all depends on the scenario, usage patters, etc. As I mentioned above, there certainly are plenty of scenarios where they do NOT make sense, but there are just as many where they do.
chadhoc
And since I didn't specify above, I should now - everything I've said would apply to a non-clustered guid key...
chadhoc
And since the schema is now posted, I can certainly agree that it is doubtful that the use of the GUID as the CLUSTER key is a good idea - you'll likely want to seriously consider clustering on something else (perhaps by adding ironically an identity attributed column and clustering on that). Another option could be to create a composite cluster by simply pre-pending the date_created column to the guid to make it a more sequential, non-random insert, but this will give you a fairly large cluster key.
chadhoc
Chadhoc, I do not understand the inner-workings enough to follow your last post. I will do more reading! What is your recommendation here? My main goal was to make the database simple, and to avoid merging issues that I know I will have if I try to merge data from two or more customers in the future. Should I make my PK NONCLUSTERED in this table?
zoran
Very tough question to answer without understanding the usage pattern of your data, types of queries (i.e. scans vs. seeks, read vs. write, etc.), relationships to other tables, etc. You'll likely want to keep the GUID usage for uniquely identifying a record across domains from the sounds of things (i.e. you need a value unique across multiple table, db's, etc.), and a nonclustered unique index/PK on this column is likely reasonable. Big question will be if you should cluster at all, and if so what should you cluster on (see the comment above for a couple options there).
chadhoc
FYI, Kimberly Tripp is a good resource for indexing, she has tons of blogs / articles covering choices involved with clustering, pks, indexes, etc. - check out http://sqlskills.com
chadhoc
Thank you. I will look at that.
zoran
A: 

The problem is that you are not allowed to insert an ID yourself (I assume this is because the engine wants to do it itself). To turn this feature on, you need to execute this query before your query:

SET IDENTITY_INSERT <tablename> ON
Franz
never do this in production code. Either use the identity column as intended or do not define it as an identiy. It is an extremely poor practice. This feature is for when you need to insert a large group of legacy records, not for the normal inserts from the application. This should never be invokked from the application if your design is correct.
HLGEM
You're right. I was just trying to answer the question, though, since he did want to insert a specific ID and I saw that as the simplest way. Me = N00b ;)
Franz
A: 

You have set the Identity property to On for the field, which means that the database creates the id when you insert a record. If you set Identity to Off for the field, you can set the value in the insert.

Alternatively, let the database create the id, then get the id that was created:

insert into someTable ();select scope_identity()

Note: A stored procedure and a parameterised query are not exclusive. I always call the stored procedures using a parameterised query.

Guffa
Similar to below, he really isn't asking how to use set ident on/off, and the problem is something different anyhow since an ident can't be a GUID
chadhoc
@Guffa - ah, I see now, It's been a long day! Will delete the comments now :)
Russ Cam
@chadhoc: Yes, you are right that a GUID can't be an identity column, but the error message clearly says that it's an identity column.
Guffa
+2  A: 

Actually, you must have some other problem, or some other column in you table, because you only would get that error if you have an IDENTITY column in your table, and IDENTITY columns can't be of the datatype uniqueidentifier - are you sure you're inserting into the same table, or you aren't using an ORM tool of some kind that is trying to specify a specific value for an identity column? Perhaps you could script the table definition out and attach it?

EDIT: Adding additional info since the question now includes the schema.

Looks like there is no identity in this particular table, so I'd first check to see if you have any triggers defined on the table in question and see if there is an attempted insert taking place in another table that uses an identity...

chadhoc
+1 exactly - there must be a IDENTITY column in the mix somewhere that's being used in the INSERT statement (and shouldn't be)
marc_s
You are right. I was connecting to the wrong database that had a table with the same name but the PK was a INT Identity field. This is also the reason why my query worked fine in Sql Management Studio but not from my code.
zoran