Feda /dev/ - No Javascript allowed

Normas
spoiler
Personas non gratas
Memes feda dev




Fyn4r

#52699 opositatest, aunque está cogido pero te puede dar ideas, supongo

Dr_Manhattan

#52699 haber opositao

1
desu

#52710 no he leído ese libro de el, si siddartha y bajo las ruedas.

gracias por aportar.

1
PiradoIV

«Amanece, que no es poco»
-- José Luis Cuerda

isvidal

Lobo estepario, me encanta:

Wei-Yu

el otro día me dijeron que sql server puede optar a usar una vista indexada en su query plan aunque no esté explícitamente en la query que haces y aún sigo pensando en ello y teniendo escalofríos

1 respuesta
B

#52716 Qué es lo escalofriante de eso? en qué casos el optimizer decide incluirla?

1 respuesta
Wei-Yu

#52717 sin pensar en la implementación que habrá en el engine, para mí no tiene sentido que el planner utilice otro objeto distinto para hacer un plan de ejecución; tendría sentido que utilizase un stored procedure sin tú indicárselo? Para mí como ignorante es el mismo caso.

Puede ser que tenga un problema de base equiparando una vista materializada a una tabla y que en el fondo sean dos objetos muy distintos y la vista materializada sea poco más que un índice sobre unos datos transformados, pero no sé lo veo como algo muy raro y que te puede morder en el culo en prod.

Y cuándo la usa pues un poco caja negra eso en términos generales... tenemos la db muy justita en el tier más pequeño de azure con solo \~700 transactions/second y ahí hay mucho atasco de IO por los imports/exports que hacemos y cuando le da un ataque de hipo de IO literalmente se le va la pinza al planner. No sé la exp que has tenido tú o ha tenido otra gente pero yo siempre lo he visto caja negra 100% (que en el fondo es un poco la idea no?).

1 respuesta
JuAn4k4

#52718 Si la indexed view tiene los datos en la tabla ya filtrada y es mejor matching por cardinalidad a los índices que hay disponibles, es probable que un full table scan sobre la materialized view sea más rentable que la alternativa.

1 respuesta
Seyriuu

Ya que estáis hablando de estos temas, si se quiere hacer un update masivo a toda una tabla db2 para poner el mismo valor en un campo (todos los registros de la tabla, el mismo campo), ¿Cuál sería la forma óptima de hacerlo?

Tener un fichero por entrada ordenado por la clave cluster de la tabla y hacer un update unitario (por dicha clave) registro a registro.
Sacar un rango de clave (todas las claves >= inicial && <= final) de, por ejemplo, el 10 % de la tabla, o sea, 10 updates de N registros.
Scar un rango de clave como antes, pero por número de registro, o sea, hacer update de 100 en 100 registros hasta terminar la tabla.

Edit: El update lo tiene que hacer un programa. No se puede interactuar directamente con la base de datos.

3 respuestas
MTX_Anubis

#52720 El primero descartado (te puede dar la friolera velocidad de 50-100 updates/seg)

Los otros dos vienen a ser lo mismo y el tamaño para ajustarlo depende de cuántos millones de registros tengas. De hecho si no es mucho puedes lanzar el update directamente a toda la tabla.

Y surgen más preguntas como si es necesario hacer batchs o deben ser actualizados a la vez por temas de inconsistencia.

2 1 respuesta
GaN2

#52720 bulk update con una única query que toque el mayor número de registros al mismo tiempo. Updates individuales tienen peor rendimiento que bulk updates cuando lo que te interesa es actualizar el mayor número de entradas al mismo tiempo.

En DB2 el UPDATE creo que no requiere el WHERE y en caso de no ponerlo se hace update del campo en toda la tabla

1 respuesta
desu
list = db.getAll()
for element in list:
  db.update(element, newElement)
db.close()
1 respuesta
Wei-Yu

#52720 no entendí bien, pero si quieres poner el mismo valor en toda la tabla puedes hacerlo en batches; tanteas para tu throughput y recursos de db cuál es el batch idóneo (10k, 50k, 100k?) y haces el update en batches. Aquí igual tirar una prueba e inspeccionar los eventos de lock para ver que no tienes lock escalation igual te compensa.

Si tu escenario es tengo una tabla con IDs, un fichero con los mismos IDs + un dato y quiero setear el dato en la tabla entonces te diría que una staging table y ya haces un batch update.

También te digo que si sólo tienes 2 ó 3 millones de filas igual hasta te puedes permitir meterle el patadón del update a pelo si tienes horas valle.

#52719 a ver, sí, hay cosas así "sencillas" que puedes inferir como lo que hablas de cardinalidades de un index vs table scan pero en términos generales creo que es muy difícil predecir qué hará el planner, hasta que no lo ejecutas (o ejecutas las queries directamente) en un sandbox no sabes bien qué esperarte.

Que aún así ya digo, que el planner pase de usar una materialized view para usar las tablas subyacentes me parece razonable, ahora que utilizar una vista "que no tiene nada que ver" "porque sí" me da terrores nocturnos, por mucho que la query utilice las mismas tablas en ambos casos.

1 respuesta
Seyriuu

#52721 Pues es gracioso, los de db2 de arquitectura es el método que han dicho que apliquemos. Un update unitario por registro, la explicación que han dado es que cuando accedes para hacer un update entra en la "paginación" de la tabla y el "puntero" se queda ahí, cuando haces el siguiente update, en vez de empezar desde el principio empieza desde el punto donde se quedó, con lo cual, es más eficiente hacer updates ordenados por la clave cluster. Ese es su razonamiento, yo de db2 poco.

El número de registros no lo sé ahora mismo, pero serán unos pocos millones. Menos de 10 imagino.

#52722 era una opción que barajaba, sí.

#52723 Eso en esencia es lo que estamos haciendo.

#52724 Esas eran las opciones 2 y 3. El escenario es que a la tabla se le ha añadido un campo nuevo (de hecho, son 5 tablas porque viva la normalización db2) y este campo inicialmente tendrá siempre un mismo valor, pero a la aplicación del proyecto cambiará.

2 respuestas
MTX_Anubis

#52725 Lo mejor es hacer la prueba

Pero vamos, sin saber de db2 ya me extraña que sea así cuando en cualquier otro engine no ocurre eso. Que ocurre con ese "puntero" con la concurencia de peticiones o se refiere a un cursor que hay que declarar y los vas recorriendo? O se refiere a la cache de la propia db2 en cuyo caso ya te digo que es mentira lo que te están diciendo y no va air más rápido 1 a 1 que en batch

Además de que ignora completamente la conexión app-db que dependiendo de donde esté tardará más que el propio update

1 respuesta
Seyriuu

#52726 yo creo que se refiere a la caché, sí, a mí también me sonó raro.

Además es que ni si quiera nos ha pedido usar un cursor for update.

Igualmente no tiene mucha relevancia, es un proceso que pasará una vez y ya, pero a mí me hubiera gustado hacerlo bien (y saber hacerlo).

Wei-Yu

cuando al de .net le piden leer de un json y no puede usar entiti freimworq

2 respuestas
aren-pulid0

#52728 me gustaría ver el rendimiento que sacas con tu propio JSON parser HAHAHAHAHAHA fpero

Soltrac

#52728 voy a quedar de ignorante seguro, pero q tiene que ver parsear un Json con EF?

1 respuesta
Wei-Yu

#52730 era un grito de auxilio una broma porque sin tirar de librerías mágicas la gente no se aclara con cosas básicas

vaya, nada más y nada menos que mi hate usual de las 2pm sobre .net

edit: y que conste que soy fan incondicional de efcore

1 respuesta
r2d2rigo

#52731 si espera que me pongo a parsear mis datos a mano con LINQ2JSON. A mamar.

GaN2

#52725 el tío de db2 ignora completamente el overhead que se produce al ejecutar updates individuales comparado con un bulk o el roundtrip entre aplicación y BBDD al ejecutar individualmente todos esos updates. Si quieres enseñarle ejemplos concretos:

https://blog.jooq.org/the-performance-difference-between-sql-row-by-row-updating-batch-updating-and-bulk-updating/?amp=1

Bulk update > Individual updates siempre a nivel de rendimiento, luego podemos hablar que no quieran tener locks a nivel de tabla completa porque haya una aplicación corriendo en el momento que se lanza el UPDATE y prefieran hacerlo uno a uno para evitar bloqueos

2 respuestas
B

@Jastro ¿se rompió el roomba?

Seyriuu

#52733 Lo de los locks podría tener sentido en otros contextos, pero en este no porque es una operativa que cuando pasásemos este proceso no va a tener ningún tipo de uso (las oficinas estarían cerradas), pero también es cierto que el de db2 desconocerá ese contexto y recomendará la metodología que no te deja la tabla bloqueada.

Aún así no sé, solo con que hiciera agrupaciones de 10 en 10 registros ya debería ser mucho más óptimo aunque siguieran siendo 400.000 updates antes que hacer 4.000.000.

Pero bueno, que o no sabrá, o en los sistemas mainframe las cosa funcionará distinta, o habrá dado la respuesta que ya tiene prefabricada y palante.

1 respuesta
GaN2

#52735 incluso con agrupaciones el rendimiento va a ser mucho mayor que hacer UPDATES individuales. Puedes agrupar nivel de UPDATE en el WHERE o en un en un bloque con BEGIN/END aunque solo te quitas la parte del roundtrip.

La idea de usar UPDATES individuales también puede ser para evitar que se les llene el transaction log si el número de entradas y el tamaño del dato a actualizar es muy grande. Al hacer UPDATES individuales el uso del transaction log debería de ser mínimo dado que el commit se hace en cada UPDATE comparado con un bulk update que se hace al final de la ejecución.

En cuanto a DB2 en mainframe comparado con LUW si son diferentes pero comparten principios como cualquier otra RDBMS. Lo que sí te digo es que los administradores de DB2 en general son especialitos y los de mainframe todavía más, cada vez que tenía que tratar con alguno del equipo de mainframe de mi antigua empresa era como pegarse de cabezazos contra un muro

1 respuesta
Seyriuu

#52736 El dato a actualizar son 2 bytes, es un "dec fixed 3,0". El resto, no lo sé, pudiera ser. Las tablas la que menos tendrá menos de 1 millón de registros, la que más igual tiene menos de 20 millones.

Yo problemas tratando con los administradores de db2 no he tenido, son majos, otra cosa es que lo que me digan me suene raro (como es el caso).

1 respuesta
GaN2

#52737 entonces no tiene lógica ninguna lo que te está diciendo si el tamaño del dato y el número de registros es ese… pero bueno, su BBDD sus reglas supongo

1
desu

Esto se explica muy fácil con una analogía/comparación.

a) realizar una petición HTTP para hacer un PUT 1M de veces
vs
b) realizar una petición HTTP para hacer un PUT 1 vez con 1M de elementos

pros y cons?

  • b mas eficiente y performance
  • b si algo falla lo gestiona internamente
  • a mas simple y facil de trackear lo que pasa

en resumen, siempre querrás hacer b porque estas delegando a otro servicio/componente el trabajo duro y gestionar los errores.
el unico motivo para realizar a es porque no EXISTE otra manera de hacerlo, es decir, para llamar HTTP de un lado a otro, si o si necesitaras como mínimo 1 petición HTTP.

por ULTIMO lo que mas os estais olvidando es el coste por operación, si es tu DB lo mismo te da igual, pero quizás en AWS te sale mas caro b que a... por ejemplo en AWS hacer transacciones entre múltiples tablas de dynamodb es MUUUCHO mas caro que gestionarlo tu a mano.

1 respuesta
Kaledros
#52739desu:

realizar una petición HTTP para hacer un PUT 1M de veces

¿Cómo haces 1M de puts con una sola petición HTTP sin tener 1M de elementos en el payload?

1 respuesta