Actualmente, tenemos una base de datos y una aplicación existentes que es completamente funcional. No tengo la capacidad de cambiar la arquitectura en este momento. Hoy, cada tabla en la base de datos tiene un campo "IsDeleted" NOT NULL BIT con un valor predeterminado de '0'. Cuando la aplicación "elimina" datos, simplemente actualiza el indicador IsDeleted a 1.
Lo que me cuesta entender es cómo deben estructurarse los índices en cada una de las tablas. En este momento, cada consulta / join / etc siempre implementa la verificación IsDeleted. Es un estándar que nuestros desarrolladores deben seguir. Dicho esto, estoy tratando de determinar si todos mis índices de claves primarias agrupadas en cada una de las tablas deben modificarse para incluir la clave primaria Y el campo BIT IsDeleted. Además, desde CADA consulta / unión / etc. debe implementar la verificación IsDeleted, ¿es una suposición apropiada que CADA índice SOLO (no agrupado también) debe incluir el campo IsDeleted como el primer campo del índice?
Otra pregunta que tengo es sobre los índices filtrados. Entiendo que podría poner filtros en los índices como "WHERE IsDeleted = 0" para reducir el tamaño de los índices. Sin embargo, dado que cada unión / consulta tendrá que implementar la verificación IsDeleted, ¿eso evitaría que se use el índice filtrado (dado que la columna IsDeleted se usa en join / query)?
Recuerde, no tengo la capacidad de cambiar el enfoque IsDeleted.
fuente
IsDeleted
columna, independientemente del almacenamiento físico, probablemente tendría sentido exponer los datos a través de dos vistas (opcionalmente en diferentes esquemas), resolviendo el problema de parametrización y cometiendo errores al acceder a datos que no deberían haber sido Accedido menos probable. El acceso a los datos base solo es relevante para los casos excepcionales en los que los datos eliminados y no eliminados deben combinarse de alguna manera, y cuando las filas realmente deben cambiarse a "eliminadas".Esta podría ser una opinión impopular, pero no creo que haya una respuesta "haz esto en todas partes" / talla única para tu pregunta.
Si tiene consultas que escanean muchas filas IsDeleted sin ningún motivo, una solución es crear un índice filtrado y no agrupado para satisfacer esa consulta.
Otra opción es crear una vista indizada que pueda ser aprovechada por una serie de consultas diferentes, que se filtra solo a las filas no eliminadas. Esto podría ser especialmente útil en Enterprise Edition, donde la coincidencia de vista indexada automática funciona sin proporcionar una
NOEXPAND
pista.Para tablas pequeñas, o tablas que se leen en gran medida, agregar índices o vistas filtradas no agrupadas o cualquier cosa realmente podría agregar una sobrecarga innecesaria a su base de datos.
fuente
Bajo el supuesto razonable de que las eliminaciones son raras, no hay cambios en los índices es una solución adecuada.
Descubrí que, tarde o temprano, uno debe buscar referencias a filas eliminadas, y las filas que están en los índices de repente valen la pena.
Tenga en cuenta que, a menos que esté utilizando vistas, debe editar todas sus consultas para incluir los filtros de todos modos.
fuente
He visto un sistema donde el indicador IS_DELETED es 0 o el valor de PK. En otros sistemas fue el negativo de la PK.
Como la mayoría de las consultas recuperaron valores mediante la clave "natural" o empresarial (a veces de múltiples campos), nunca consultaron por PK, excepto a través de combinaciones; pero siempre agregaron un AND IS_DELETED = 0 al final para la tabla principal y para cualquier tabla unida.
Este sistema también tenía una tabla de auditoría para cada tabla transaccional que rastreaba los cambios; y la aplicación tenía una función para mostrar todos los cambios de datos, incluidos los datos eliminados.
fuente
Espero que tenga el derecho y la capacidad de cambiar la consulta.
Quería decir un punto importante, espero poder explicarlo.
En consulta compleja dónde
Transaction table
yMaster
tablas se usan ambas.Usar
IsDeleted=0
solo en laTransaction
mesa. No utilizar enMaster
mesa.Ejemplo,
No tiene sentido
c.isdeleted=0
(usar en laCategory
tabla). Es innecesario.Del mismo modo, ¿hay algún punto en el uso
P.isdeleted=0
?Porque quiero todos los pedidos sin recuperar y sus detalles.
Cómo se
Product
puede eliminar cuandoOrder
esActive
o dondeProductid
sea referencia.De esta manera, si depura cuidadosamente en una consulta importante, puede eliminar algo de isdeleted = 0.
No cree ciegamente un índice filtrado, primero seleccione todas esas consultas muy importantes y lentas.
Optimice esas consultas lentas y luego solo decida sobre el índice filtrado o ajuste el índice.
fuente