En muchos diseños de bases de datos relacionales hay campos a los que se hace referencia en otras tablas.
Por ejemplo, considere una tabla de usuario con un nombre de usuario único y una segunda tabla que almacena datos de dirección.
Una disposición posible, que diría que es el enfoque común, porque he observado en la mayoría de los programas, es usar identificadores de incremento automático como este:
Table users
===========
userId int primary auto_increment
userName varchar unique
Table adressdata
==========
userId int references users.userId
adress_type varchar // for example country
address_value varchar // for example US
(you probably also want to put a unique key on (userId,adress_type))
Así es como solía hacerlo y cómo lo he visto en la mayoría de los casos.
Otra forma sería:
Table users
===========
userName varchar primary
Table adressdata
==========
userName varchar references users.userName
adress_type varchar // for example country
address_value varchar // for example US
(you probably also want to put a unique key on (userName,adress_type))
Aquí almacenamos el nombre de usuario completo también en la tabla de dirección de datos.
Para mí esto tiene las siguientes ventajas:
Puede seleccionar el nombre de usuario directamente desde la tabla sin la necesidad de unirlo a otra tabla. En este ejemplo, esto es desde el punto de vista de la aplicación, probablemente no tan relevante, pero es solo un ejemplo.
Puede ser más fácil escalar la base de datos en un entorno de replicación maestro-maestro, porque no hay conflictos de aumento automático.
Pero también las desventajas:
- Los requisitos de espacio para el índice y los datos (pero probablemente más relevante será el índice) en el campo de la segunda tabla son más altos.
- Un cambio del nombre de usuario necesitaría propagarse a todas las tablas, lo que consume más recursos que simplemente cambiarlo en una tabla y dejar los identificadores como están.
En mi opinión, es mucho más fácil trabajar con campos de texto y no usar identificadores de incremento, y las compensaciones son mínimas y en la mayoría de las aplicaciones no son relevantes.
Por supuesto, algunos objetos SE identifican con un número creciente por su naturaleza (por ejemplo, las publicaciones del foro deberían recibir una identificación creciente porque probablemente no haya otro campo único como el título más o menos).
Pero antes de comenzar a diseñar los diseños de mi base de datos de una manera completamente diferente, me gustaría saber si hay cosas en las que no pensé.
¿Hay alguna mejor práctica?
¿Hay pros / contras que no pensé y cuyo efecto puede surgir en un momento posterior en el tiempo?
¿Cómo diseñas personalmente las bases de datos con respecto a los puntos anteriores y por qué?
Publicaré desde mi experiencia, que probablemente será muy diferente de lo que podrían sugerir varios DBA. Estoy orientado principalmente hacia la combinación de rendimiento y facilidad de mantenimiento al diseñar bases de datos para varios proyectos.
Yo nunca, nunca utilizar una clave natural para la clave principal. Especialmente si uso MySQL / InnoDB. Todavía no he visto ningún beneficio en el uso de una clave natural, por lo general, lo que veo son implicaciones de rendimiento, si es que nada. En negrita "nunca, nunca" solo porque las claves naturales solían crear cerdos de rendimiento para mis proyectos. El sustituto (entero) siempre fue una mejor opción. Puede que algunos no estén de acuerdo, pero vivimos en un mundo donde el rendimiento juega un papel importante en la teoría.
Cuando se trata de JOIN, no trato de evitarlos a toda costa, pero tiendo a optimizarlos. Intento abusar del índice agrupado de InnoDB (clave primaria) tanto como sea posible. Si las uniones se realizan a través de PK, entonces son extremadamente rápidas. También tiendo a evitar los FK donde no tienen sentido. Honestamente, no me importaría tanto la integridad de los datos cuando se trata de vincular usuarios y su información de dirección. Lo aplicaría al vincular facturas a artículos para los usuarios. El uso excesivo de FK es una exageración y una pesadilla para mantener después de hacer referencia a todo, pensando que es un gran diseño para mantener relaciones en todo el lugar. En algún momento, las cosas deben cambiar y cuando MySQL comienza a quejarse con el error 150 constantemente, solo quiere volver a casa.
También mencionó la replicación y evitar conflictos debido a la naturaleza de los aumentos automáticos. Tenía un proyecto donde teníamos una cantidad de bases de datos que almacenaban información de ventas de productos, la cantidad de bases de datos era variable. Todos los días las bases de datos se replicaban en una base de datos "maestra" que usábamos para ejecutar informes. La forma en que evité los enfrentamientos PK fue creando una clave primaria compuesta de una parte de auto_increment y otra parte INT que denotaba la ubicación de donde provenía el registro. De esa manera pude rastrear de dónde vinieron las cosas y no perdí nada (los productos tenían la misma ID, solo se cambió el identificador de ubicación).
fuente