Quantcast
Channel: West Wind Message Board Messages
Viewing all articles
Browse latest Browse all 10393

Re: NewId stored procedure

$
0
0
Re: NewId stored procedure
West Wind Client Tools
Re: NewId stored procedure
Mar. 25, 2013
07:15 am
3QV0FK38OShow this entire thread in new window
Gratar Image based on email address
From:Matt Slay
To:Rick Strahl
Rick - I'm currently calling on the regular wwBusiness.Save() to save the record to Sql Server.

The real reason for this question is this: My current business app is in VFP using DBFs. I'm converting it to use Sql Server backend. (I'm very close to being finished!!!) So, my goal is to wind up with a database in Sql Server that is also well suited for Entity Framework so that I can begin developing .Net apps against the same database while the VFP app continues to run for several more years.

I need a DB that supports both wwBusiness and EF very well.

I assumend EF works better with an Identity column where the DB assigns the PK values, or that it may even *require* this. I'm not sure yet? Also the examples I've seen use Identity column.

If EF does work better this way, then what's the correct to override your base Save() method over to this ExecuteNonQuery() method that you have suggested? Looking at that code, I see that it calls loSql.Execute() on to execute a SQL Insert command that it creates using SqlBuildInsertStatementFromObject().

Ideally, wouldn't it be nice if the base wwBusiness.Save() had provisions for handling this need? It seems like a comman scenario where some VFP apps might assign the ID with CreateNewID() and some night need to let SQL Server assign it via the Identity column. Maybe a flag on wwBusiness that indicates "Sql Serder Identity column will assignt he PK". and then it would fetch it back and store it on the cPKField automatically.


Matt,

You'd need to override NewId() to be empty, then after each insert you need to call SELECT ScopeIdentity() to

? loSql.ExecuteNonQuery("insert into blah (field1,field2) values (1,2)") ? loSql.Executenonquery("select Scope_Identity()")

Alternately you can also use INSERT INTO ... OUTPUT INSERT.* which returns the entire new record in SQL 2008 and later.

+++ Rick ---


So, if I use CreateNewId() to pre-assign a PK it's all pretty easy to then use this PK as a foreign key on a few new child records that I also need to save.


However, what if I want to setup SQL Server to use an Identity column and let it assign the PK when the record is added... What's the best strategy to use to get that PK right back so I can use it for FK in child records???



Hmm... yeah that code is pretty old...

This will do it:

EXEC dbo.sp_executesql @statement = N'ALTERPROCEDURE [dbo].[sp_ww_NewID] @cName char(30), @nRetval int OUTPUTASUPDATE wws_Id SET id = id + 1, @nRetval = id + 1WHERE TableName = @cNameif @@ROWCOUNT< 1BEGINinsertinto wws_id (Tablename,Id) values (@cName,1)set @nRetval = 1END 'ENDGO

The code doesn't need to check for next id because the Update is a single statement that intrinsicly runs in a transaction. it's not possible for for two updates to run completely simultaneously on the same table while the table is looking at a specific value as it locks the record (or possibly even the entire table) during the update.

+++ Rick ---


Rick - I've noticed that the CreateNewId() method, when working with FoxPro DBF tables, will add the tablename to the ww_id table if it is not already present, but in Sql Server mode, it uses a stored proceure which does not add the table name to wws_id if it is not already present (like it does on the FoxPro datamode). It also does not attempt to verify that the next PK value is not already used in the target table, as it does for the FoxPro DBF version.

I'm moving my app from DBFs to Sql Server, and it looks like you've just got to manually prep the wws_id table with each table name and the correct next ID value to use.







Viewing all articles
Browse latest Browse all 10393

Trending Articles