Welcome to Sign in | Help
in Search

obtinere camp identity in avans pentru trimiterea catre client

Last post 09-09-2009, 12:05 PM by victordomain. 10 replies.
Sort Posts: Previous Next
  •  08-31-2009, 11:37 AM 7534

    obtinere camp identity in avans pentru trimiterea catre client

    Salut,

    Asadar avem urmatoarea situatie. O tabela (tabela1), doua coloane (col_key [cheie primara], col_math).

    Col_key este de tip identity si din cunostintele mele la fiecare insert acea valoare va fi incrementata cu 1(sau alta valoare). Problema este ca valoare lui col_math depinde strict de valoarea lui col_key proaspat generat.

    Adica atunci cand eu fac un insert (un insert gol initial pentru ca nu stiu inca valoarea lui col_key) valoare lui col_math sa ia automat valoarea lui

    col_key*2 (doar ca exemplu pentru ca e cu totul o alta operatie ce nu are legatura cu matematica si nu poate fi tranpus in TSQL).

    Inseram un camp vid si rezulta sa zicem col_key = 417. Acum trebuie sa gasesc o metoda prin care acel col_key sa-mi fie returnat in aplicatie, acolo sa fac operatiile mele ca la final sa fac un update de tipul

    UPDATE tabela 1 set col_math= valoare_mea_ce_depinde_de_col_key where col_key=417

    Problema este ca aplicatia este concurenta si pot sa am chiar 20-30 de clienti conectata la ea asadar o abordare de tipul:

    SELECT col_key top 1 where col_math = null nu poate functiona deoarece pot sa am mai multi clienti care tocmai au facut acel insert null si deci mi se poate returna col_key-ul corespunzator altui client.

    Metoda la care m-am gandit eu:
    Pe partea de server fac o procedura stocata care sa-mi faca acel insert vid si-mi returneaza fix acel col_key .
    Pe partea de client apelez procedura stocata si fac acel update.

    Acum nu stiu cum sa fac procedura aceea stocata ca sa fi sigur ca fiecare client concurent primeste exact col_key-ul care trebuie. Sau mai pe scurt, cum generez acel identity in avas (dar sa mai fie si rezervat) urmad ca apoi sa-l transmit catre client.

    Stiu ca e simplu dar nu am experienta cu SQL.

    Multumesc pentru sprijin.

  •  08-31-2009, 12:14 PM 7535 in reply to 7534

    Re: obtinere camp identity in avans pentru trimiterea catre client

    insert into tabela (col_math) values(0);select scope_identity();

    asa poti sa fii sigur ca iti intoarce ID-ul recordului proaspat inserat.
    Sper ca am inteles bine ce vroiai...!
    Spor!
  •  08-31-2009, 1:53 PM 7536 in reply to 7535

    Re: obtinere camp identity in avans pentru trimiterea catre client

    Dar daca intre insert into tabela (col_mth) values(0); si select scope_identity(); un alt user a facut un insert folosind aceeasi metoda si acel scope_identity() apartine de fapt altui insert facut cu o milisecunda mai devreme?

    Sau sa inteleg ca aceste doua linii trebuie sa fie de fapt incluse intr-o procedura stocata si astfel cele doua operatii sunt cumva vazute ca "atomice" (adica executate deodata)?

    Multumesc.

  •  08-31-2009, 2:08 PM 7537 in reply to 7536

    Re: obtinere camp identity in avans pentru trimiterea catre client

    "Returns the last identity value inserted into an identity column in the same scope. A scope is a module: a stored procedure, trigger, function, or batch. Therefore, two statements are in the same scope if they are in the same stored procedure, function, or batch."

    http://msdn.microsoft.com/en-us/library/ms190315.aspx

    (Adica le executi una dupa alta)
    Cătălin D.
  •  08-31-2009, 2:21 PM 7538 in reply to 7537

    Re: obtinere camp identity in avans pentru trimiterea catre client

    daca executi linia scrisa de mine mai sus si un alt user executa aceeasi linie la 1 milisecunda mai tirziu, fiecare o sa primeasca corect ID-ul recordului respectiv (cel inserat de el).
  •  08-31-2009, 2:22 PM 7539 in reply to 7537

    Re: obtinere camp identity in avans pentru trimiterea catre client

    Adica este EXACT ce-mi trebuie.

    Multumesc mult.

    Topic closed!

  •  08-31-2009, 2:27 PM 7540 in reply to 7536

    Re: obtinere camp identity in avans pentru trimiterea catre client

    In descrierea initiala a scenariului mentionati o procedura stocata pentru inserarea unei noi inregistrari.
    Subscriu la aceasta idee sugerand si includerea unui parametru de output pentru preluarea valorii generate pentru coloana cu proprietatea IDENTITY.

    Cristian Andrei Lefter, SQL Server MVP
    MCT, MCSA, MCDBA, MCAD, MCSD .NET,
    MCTS, MCITP - Database Administrator SQL Server 2005
    http://sqlserver.ro
  •  08-31-2009, 4:50 PM 7547 in reply to 7540

    Re: obtinere camp identity in avans pentru trimiterea catre client

    Procedura arata cam asa:

    CREATE PROCEDURE Indentity1
    AS
    insert into tabela1 default values
    return SCOPE_IDENTITY()
    GO

    Credeti ca este ok? Mie imi returneaza exact ce trebuie.

  •  08-31-2009, 5:14 PM 7549 in reply to 7547

    Re: obtinere camp identity in avans pentru trimiterea catre client

    Nu este OK

    "The calling stored procedure or Transact-SQL statement must be rewritten to use the SCOPE_IDENTITY() function which will return the latest identity used within the scope of that user statement, and not the identity within the scope of the nested trigger used by replication."


    @@IDENTITY and SCOPE_IDENTITY return the last identity value generated in any table in the current session. However, SCOPE_IDENTITY returns the value only within the current scope; @@IDENTITY is not limited to a specific scope.

    Pentru a intelege mai bine despre ce este vorba, te rog sa analizezi exemplul de mai jos:
    create table dbo.[Tabela cu trigger] (
    coloana int identity (1,1)
    )

    create table dbo.[Trigger-ul face insert] (
    coloana int identity (10000,1000)
    )
    go

    create trigger trg_ on dbo.[Tabela cu trigger]
    for insert as begin
    insert into dbo.[Trigger-ul face insert]default values
    end
    go


    insert into dbo.[Tabela cu trigger] default values
    select @@Identity as [@@Identity], scope_identity() as [scope_identity]



    PS: Coloana [@@Identity] va avea valoarea 10000 (identity "produs" in trigger) iar celalalta coloana va avea valoarea 1 ("produs" in procedura)


    LE: mesajul initial era asa:
    Procedura arata cam asa:
    CREATE PROCEDURE Indentity1
    AS
    insert into tabela1 default values
    return @@IDENTITY
    GO
    Credeti ca este ok? Mie imi returneaza exact ce trebuie."

    Cătălin D.
  •  09-01-2009, 8:43 AM 7550 in reply to 7549

    Re: obtinere camp identity in avans pentru trimiterea catre client

    SCOPE_IDENTITY este functia pe care trebuie sa o folositi. Cum a mentionat si Catalin, in cazul existentei unui trigger e posibil sa obtineti rezultate gresite.

    Cristian Andrei Lefter, SQL Server MVP
    MCT, MCSA, MCDBA, MCAD, MCSD .NET,
    MCTS, MCITP - Database Administrator SQL Server 2005
    http://sqlserver.ro
  •  09-09-2009, 12:05 PM 7585 in reply to 7550

    Re: obtinere camp identity in avans pentru trimiterea catre client

    Multumesc foarte mult pentru raspunsuri.

     

    M-am lamurit, asadar ramane return SCOPE_IDENTITY()

     

View as RSS news feed in XML
Powered by Community Server (Commercial Edition), by Telligent Systems