Italian community of Lazarus and Free Pascal

Programmazione => Databases => Topic aperto da: Maverich - Aprile 07, 2012, 08:00:51 pm

Titolo: uso di "Insert" con Query Join
Inserito da: Maverich - Aprile 07, 2012, 08:00:51 pm
Ho provato con SQLQuery (da SQLdb) e con ZQuery delle Zeos

SQLQuery mette il Dataset sempre in ReadOnly, neppure e' possibile eseguire Insert
ZQuery non permette il Post

"cannot update a complex query with more one table"

per tutti i campi in Join ho settato i Flag della sezione ProviderFlag fnUpdate e pfnWhere = False
(in Delphi componenti DbExpress se non setto a False mi segnale che campo JOIN e' inesistente)

questa la query

SELECT TB_ANAGRAFE.*,
 USR_COM.COMUNE      AS COMUNERESIDENZA,
 USR_COM1.COMUNE AS COMUNERILASCIO,
 USR_COM2.COMUNE AS COMUNENASCITA,
 USR_COM3.COMUNE AS COMUNEIMMIGRAZIONE,
 USR_COM4.COMUNE AS COMUNEEMIGRAZIONE,
 USR_COM5.COMUNE AS COMUNEDECESSO

FROM TB_ANAGRAFE
LEFT OUTER JOIN TB_COMUNI  AS USR_COM ON TB_ANAGRAFE.ID_COMUNERESIDENZA=USR_COM.ID_COMUNE
LEFT OUTER JOIN TB_COMUNI  AS USR_COM1 ON TB_ANAGRAFE.ID_COMUNERILASCIO=USR_COM1.ID_COMUNE
LEFT OUTER JOIN TB_COMUNI  AS USR_COM2 ON TB_ANAGRAFE.ID_COMUNENASCITA=USR_COM2.ID_COMUNE
LEFT OUTER JOIN TB_COMUNI  AS USR_COM3 ON TB_ANAGRAFE.ID_COMUNEIMMIGRAZIONE=USR_COM3.ID_COMUNE
LEFT OUTER JOIN TB_COMUNI  AS USR_COM4 ON TB_ANAGRAFE.ID_COMUNEEMIGRAZIONE=USR_COM4.ID_COMUNE
LEFT OUTER JOIN TB_COMUNI  AS USR_COM5 ON TB_ANAGRAFE.ID_COMUNEDECESSO=USR_COM5.ID_COMUNE

Questo il tentativo

  ZQuery1.Insert;
  ZQuery1.FieldByName('ID_ANAGRAFE').AsInteger := 20;
  ZQuery1.FieldByName('ID_OPERATORE').AsInteger := 7;
  ZQuery1.FieldByName('COGNOME').AsString := 'Prova Test';
  ZQuery1.FieldByName('ID_COMUNERILASCIO').AsInteger := 156;
  ZQuery1.Post;
Titolo: Re:uso di "Insert" con Query Join
Inserito da: Maverich - Aprile 08, 2012, 04:12:27 pm
utilizzando il costrutto INSERT INTO <NOMETABELLA> (campi) VALUES (valori dei campi),
la Query di inserimento avviene senza problemi.

es:

   ZQuery1.SQL.Clear;
   ZQuery1.SQL.Add('INSERT INTO TB_ANAGRAFE (');
   ZQuery1.SQL.Add('ID_ANAGRAFE,');
   ZQuery1.SQL.Add('ID_OPERATORE,');
   ZQuery1.SQL.Add('COGNOME,');
   ZQuery1.SQL.Add('NOME,');
   ZQuery1.SQL.Add('DATANASCITA,');
   ....
   ZQuery1.SQL.Add(' ) VALUES ( ');
   ZQuery1.SQL.Add(QuotedStr(IntToStr(idAnagrafe)) + ',');
   ZQuery1.SQL.Add(QuotedStr(IntToStr(idOperatore)) +',');
   .....
   ZQuery1.ExecSQL;

-- usare QuotedStr e' equivalente a #39 + <stringa> + #39 --
es:

   ZQuery1.SQL.Add(#39 + IntToStr(idOperatore) + #39 + ',');
   ZQuery1.SQL.Add(QuotedStr(IntToStr(idOperatore)) +',');
Titolo: Re:uso di "Insert" con Query Join
Inserito da: xinyiman - Aprile 09, 2012, 11:31:58 am
Scusa il ritardo, questo avviene perchè tu cerchi di aggiungere un record ad un recordset complesso (con delle join) e questo in lazarus non si può fare. Puoi invece usare il costrutto SQL insert come giustamente hai proposto tu.

Ciao
Titolo: Re:uso di "Insert" con Query Join
Inserito da: Maverich - Aprile 10, 2012, 02:26:37 pm
Allego un'esempio (non hopotuto inserire il DB Firebird (max allegato = 128k)

Noto un'altro errore eseguendo il report
click su Report, visulizza, click su Chiude (distruggo)
click su Report
modulo lr_view.pas line 236 FWindow.PreviewPanel.Parent := self;

uso Lazarus 0.9.31 - Fpc 2.7.1
Titolo: Re:uso di "Insert" con Query Join
Inserito da: Stilgar - Aprile 18, 2012, 03:39:39 am
Maverik per queste cose dovrebbe venirti incontro l'oggetto di UPDATE da associare alla query.
In pratica il meccanismo sotto è semplice.
TQuery estrae i dati e TUpdateSQL esegue le cose verso il DB.

A seconda della configurazione (Chiave, Record) TQuery passa o i campi chiave o tutto il record modificato (OLD e NEW a seconda delle esigenze) a TUpdateSQL.

In pratica (per chi mastica di progettazione) query delega ad updatesql di fare le operazioni.
TUpdatesql, alla fine non è che un contenitore di query (se ricordo bene). InsertSQL, DeleteSQL, UpdateSQL.
Se non c'è questa associazione è come se stessi lavorando su una "tabella".
Effettivamente SQLDb come package non ha questa classe, ma TSQLQuery ha le propery InsertSQL ecc.
Spero di averti dato qualche dritta utile.

Stilgar
PS:
Controllando il codice "funzionante" ho notato una cosa, non so se per scelta di tempi o gusto personale, come mai hai cablato i valori da inserire?
Codice: [Seleziona]
  ZQuery1.SQL.Add(QuotedStr(IntToStr(idAnagrafe)) + ',');
Potevi utilizzare i PARAMS Standard.... o no?
Con una stringa "omnicomprensiva" dell'insert avresti avuto la possibilità di usare i "?" (Zeos) o :nome_parametro (Delphi standard) come segna posti. O mi sono perso qualche cosa, vista l'ora ;)
Titolo: Re:uso di "Insert" con Query Join
Inserito da: xinyiman - Aprile 18, 2012, 08:02:10 am
Stilgar sarebbe bello scrivere un articoletto al riguardo con annesso esempio. Ti va di farlo?! Così poi ti autorizzo a pubblicarlo sulla community!
Titolo: Re:uso di "Insert" con Query Join
Inserito da: Stilgar - Aprile 18, 2012, 09:13:09 am
Si potrebbe anche pensarci seriamente, attendo con trepitazione che esca la patch che aspetti per avere un search degli articoli ;)
Titolo: Re:uso di "Insert" con Query Join
Inserito da: xinyiman - Aprile 18, 2012, 09:17:17 am
A quella l'aspetto pure io! Prima o poi la faranno! Nel mentre se vuoi iniziare a buttare giù una bozza dell'articolo e quando hai fatto me lo dici così ti rendo utente con privilegi "Scrittore" così potrai andarlo ad inserire nella sezione How To