Sugerencias para Query

05/07/2004 - 18:23 por RCA | Informe spam
Hola grupo,

Tengo un SP que realiza varios procesos internamente. En su totalidad son
ingresos de datos con algunnas excepciones donde se realizan
actualizaciones. En total son unas 15 tablas aproximandamente.

Lo que necesito es controlar la inserción/actualización de datos para cada
una de estas; en caso de haber error, guardar este en una tabla de Logs ya
definida . He estado investigando la utilización de Begin Transaction con
sus respectivos Commit o Rollback, pero me gustaría tener alguna
recomendación por parte de ustedes en la construcción del Query.

La lógica del código T-SQL sería algo así:

SP_CargaDeDatos
Begin

Insert TablaDestino1 Campo1,Campo2,Campo3
Select Campo1
Campo2
Campo3
From TablaOrigen1
Insertar en el Proceso 1.', 16, 1)


Insert TablaDestino2 Campo1,Campo2,Campo3
Select Campo1
Campo2
Campo3
From TablaOrigen2
Actualizar en el Proceso 2.', 16, 1)

Insert TablaDestino3 Campo1,Campo2,Campo3
Select Campo1
Campo2
Campo3
From TablaOrigen3
Insertar en el Proceso 3.', 16, 1)
.
.
.
etc.

End

¿Cuál es la mejor forma de controlar las transacciones? ¿Donde las utlizo
para guardar el error en la tabla de Logs?

Gracias.

RCA.

Preguntas similare

Leer las respuestas

#6 SqlRanger [MVP .NET]
06/07/2004 - 13:58 | Informe spam
Javier,

No estoy muy seguro de que esa técnica que usas sea conveniente en la
mayoría de los casos. Me explico. Según parece, la ejecución es más rápida
en caso de datos no válidos puesto que no hay que hacer Rollback al hacerse
las comprobaciones al principio. Sin embargo en caso de que los datos sean
válidos, parece ser que la ejecución es más lenta puesto que las
comprobaciones se hacen dos veces.

La cuestión es entonces:

¿ El aumento del rendimiento obtenido para los casos de datos no válidos
compensa con creces la disminución de rendimiento obtenida en el caso de
datos válidos?

¿Qué porcentaje de transacciones contienen datos no válidos?

¿No es cierto que la mayoría de las transacciones tienen datos válidos y
concluyen con éxito?

¿No es cierto que muchas validaciones se pueden hacer en el cliente sin
tener que acceder a SQL Server, y que esto evita enviar transacciones con
datos no válidos?

Saludos:

Jesús López
MVP .net
Respuesta Responder a este mensaje
#7 RCA
06/07/2004 - 16:08 | Informe spam
Estimados,

Gracias por sus aportes.

Explico otros detalles del proceso en sí. Este se realizará de manera BATCH,
es decir, no hay ninguna capa o interfaz que manipule los datos antes de
realziar las operaciones de inserción/actualización.

La idea del proceso es el traspaso de datos de una BD FUENTE a una BD
DESTINO.

En la FUENTE los datos vienen diariamente. En la de DESTINO se van
almacenando los HISTÓRICOS para ciertas tablas. En las históricas siempre se
realiza una inserción de datos. Para las otras (con un máximo de 20
registros cada una) es necesario validar si el dato existe o no para la
inserción, o si ocurrió alguna modificación en alguno para la actualización.
Para estas ultimas creo que se puede utilizar la idea que propone Javier, ya
que aquí es probable que hayan cambios y con 20 registros no creo que se
consuman muchos recursos.

Total Tablas Info. DIARIA : 11
Total Tablas Info. HISTORICA : 4

Lo que tengo claro aún es cómo manejar el rollback en sí.

Basta con hacer esto??...

Begin Tran
Insert...
Select Campo1,
Campo2 ,
Campo3,
CampoN
From Tabla
If @@Error <> 0 Then
Begin
Raiserror(...)
Insert Into Tb_Logs 'Error...'
Rollback
End

Commit


"SqlRanger [MVP .NET]" escribió en el mensaje
news:OD$
Javier,

No estoy muy seguro de que esa técnica que usas sea conveniente en la
mayoría de los casos. Me explico. Según parece, la ejecución es más rápida
en caso de datos no válidos puesto que no hay que hacer Rollback al


hacerse
las comprobaciones al principio. Sin embargo en caso de que los datos sean
válidos, parece ser que la ejecución es más lenta puesto que las
comprobaciones se hacen dos veces.

La cuestión es entonces:

¿ El aumento del rendimiento obtenido para los casos de datos no válidos
compensa con creces la disminución de rendimiento obtenida en el caso de
datos válidos?

¿Qué porcentaje de transacciones contienen datos no válidos?

¿No es cierto que la mayoría de las transacciones tienen datos válidos y
concluyen con éxito?

¿No es cierto que muchas validaciones se pueden hacer en el cliente sin
tener que acceder a SQL Server, y que esto evita enviar transacciones con
datos no válidos?

Saludos:

Jesús López
MVP .net



Respuesta Responder a este mensaje
#8 Javier Loria
06/07/2004 - 17:44 | Informe spam
Hola Jesus:
Levantas un buen punto. Voy a trabajar en un demostracion y la posteo.
Mientras tanto piensa en los principios generales de desarrollo de
software, el patron que posteo esta basado en un concepto llamada
Programacion Defensiva, que a su vez esta basado en el concepto de Manejar a
la Defensiva. El manejar a la defensiva asume que debemos protegernos de
los errores que puedan cometer otros choferes para evitar accidentes.
Igualmente un procedimiento puede protegerse de los errores que cometan
otras funciones o codigo.
A las primeras 3 preguntas te digo que efectivamente la mayoria de los
casos son exitosos, pocas veces los datos tienen datos no validos y la
mayoria concluye con exito. El problema es que el costo de las que NO lo son
es de 10 a 100 veces mas alto que los que no lo son, ya que para entoces se
ha grabado en el Transaction Log, (Disco Duro 500 veces mas lento que la
memoria) y se han bloqueado las tablas.
De la 4 pregunta me rio, demasiadas veces cuando construyo Almacenes de
Datos me encuentro con cantidades industriales de basura.
Saludos,

Javier Loria
Costa Rica
Se aprecia la inclusion de DDL (CREATE, INSERTS, etc.)
que pueda ser copiado y pegado al Query Analizer.
La version de SQL y Service Pack tambien ayuda.

SqlRanger [MVP .NET] escribio:
Javier,

No estoy muy seguro de que esa técnica que usas sea conveniente en la
mayoría de los casos. Me explico. Según parece, la ejecución es más
rápida en caso de datos no válidos puesto que no hay que hacer
Rollback al hacerse las comprobaciones al principio. Sin embargo en
caso de que los datos sean válidos, parece ser que la ejecución es
más lenta puesto que las comprobaciones se hacen dos veces.

La cuestión es entonces:

¿ El aumento del rendimiento obtenido para los casos de datos no
válidos compensa con creces la disminución de rendimiento obtenida en
el caso de datos válidos?

¿Qué porcentaje de transacciones contienen datos no válidos?

¿No es cierto que la mayoría de las transacciones tienen datos
válidos y concluyen con éxito?

¿No es cierto que muchas validaciones se pueden hacer en el cliente
sin tener que acceder a SQL Server, y que esto evita enviar
transacciones con datos no válidos?

Saludos:

Jesús López
MVP .net
Respuesta Responder a este mensaje
#9 SqlRanger [MVP .NET]
07/07/2004 - 11:02 | Informe spam
En principio sí que bastaría, pero este código tiene algunos problemillas:

Begin Tran
Insert...
Select Campo1,
Campo2 ,
Campo3,
CampoN
From Tabla
If @@Error <> 0 Then
Begin
Raiserror(...)
Insert Into Tb_Logs 'Error...'
Rollback
End

Commit

Si se produce algún error lo que insertas en la tabla Tb_Logs también se
deshace ya que está en la misma transacción.

Yo utilizaría un código como este:

Begin Tran
Insert...
Select Campo1,
Campo2 ,
Campo3,
CampoN
From Tabla
If @@Error <> 0 Then
Begin
Raiserror(...)
Insert Into Tb_Logs 'Error...'
Rollback
goto Errores
End

Commit
RETURN
Errores:
Insert Into Tb_Logs 'Error...'

Existe otra alternativa a registrar los errores en una tabla, consiste en
registrarlos en el registro de errores de SQL Server y el el registro de
suscesos de Windows. Para ello tienes dos opciones::

(1) Usar la opción WITH LOG con RaisError
(2) Añadir un mensaje de error con sp_addmessage y que este mensaje de error
sea registrado.

Saludos:

Jesús López
MVP .net
Respuesta Responder a este mensaje
#10 Carlos Sacristan
07/07/2004 - 11:15 | Informe spam
Jejejeje. La verdad es que con la gozada de respuestas así, ¿quién se
atreve a replicar?

A falta de "Fernandos Guerreros", los "esequelerangers" tampoco se
quedan cortos en sus explicaciones ;-)


Un saludo

-
"Sólo sé que no sé nada. " (Sócrates)

Por favor, responder únicamente al foro
Se agradece la inclusión de sentencias DDL


"SqlRanger [MVP .NET]" escribió en el mensaje
news:eWdNn3$
Javier,

Hagamos unas pocas cuentas para tener una idea más concreta de la cuestión.

Tenemos que sin usar el patrón "programación a la defensiva"

(1) Tm = Tv * Pv + Tnv * Pnv

Donde:

Tm: es el tiempo medio de una transacción sin programación a la defensiva
Tv: tiempo medio de una transacción con datos válidos sin programación a la
defensiva
Pv: porcentaje (en tanto por uno) de transacciones con datos válidos
Tnv: tiempo medio de una transacción con datos no válidos sin programación a
la defensiva
Pnv: porcentaje (en tanto por uno) de transacciones con datos no válidos

Y usando el patrón "programación a la defensiva":

(2) Tmd = Tvd * Pv + Tnvd * Pnv

Donde:

Tmd: es el tiempo medio de una transacción con programación a la defensiva
Tvd: tiempo medio de una transacción con datos válidos con programación a la
defensiva
Pv: porcentaje (en tanto por uno) de transacciones con datos válidos
Tnvd: tiempo medio de una transacción con datos no válidos con programación
a la defensiva
Pnv: porcentaje (en tanto por uno) de transacciones con datos no válidos

Para que la programación a la defensiva sea más eficiente tendrá que
culplirse que:

(3) Tm > Tmd

o lo que es lo mismo:

(4) Tv * Pv + Tnv * Pnv > Tvd * Pv + Tnvd * Pnv

Hagamos ahora algunas suposiciones:

Debido a que con la programación a la defensiva en una transacción con datos
válidos las restricciones de comprueban dos veces, el tiempo será mayor,
supongamos que es por ejemplo un 25% mayor . Es decir:

(5) Tvd = 1,25 * Tv

Debido a que sin programación a la defensiva hay que hacer un Rollback
cuando los datos no son válidos, el tiempo de una transacción con datos no
válidos es muy superior a de una con los datos válidos, supongamos que es
por ejemplo 20 veces superior. Es decir:

(6) Tnv = 20 * Tv

Debido a que con programación a la defensiva en una transacción con datos no
válidos no se hace ninguna modificación, el tiempo es incluso menor que el
de una transacción con datos válidos sin programación a la defensiva,
pongamos que es la mitad. Es decir:

(7) Tnvd = 0,5 * Tv

Como además se cumple:

(8) Pv + Pnv = 1

O lo que es lo mismo:

(9) Pv = 1 - Pnv

Sustituyendo (9), (7), (6) y (5) en (4) tenemos:

(10) Tv * ( 1- Pnv ) + 20 * Tv * Pnv > 1,25 * Tv * ( 1 - Pnv ) + 0,5 * Tv *
Pnv

Operando:

(11) 1 + 19 * Pnv > 1,25 - 0,75 * Pnv <=> 19,75 * Pnv > 0,75 <=> Pnv >
0,75/19,75

Con lo que al final nos queda:

(12) Pnv > 3,8%

Es decir, que con las suposiciones que hemos hecho anteriormente, para que
usar este patrón sea más eficiente que no usarlo, el porcentaje de
transacciones con datos no válidos tendría que ser superior al 3.8 %, lo que
a mi jucio es bastante improbable.

Desde luego, estas suposiciones son sólo eso, suposiciones, aunque creo que
estos números no deben de andar demasiado desencaminados. Habría que motar
un laboratorio o usar sistemas en producción y monitorizar para ver cuales
son en realidad estos números.

Saludos:

Jesús López
MVP .net
Respuesta Responder a este mensaje
Ads by Google
Help Hacer una preguntaSiguiente AnteriorRespuesta Tengo una respuesta
Search Busqueda sugerida