Database
 sql >> Base de Dados >  >> RDS >> Database

Como projetar um modelo de banco de dados para um sistema de reserva de cinema


Você gosta de ir ao cinema? Você já considerou como é o design do banco de dados por trás do sistema de reservas? Neste artigo vamos preparar um modelo de banco de dados de exemplo para uma sala de cinema.

Existem algumas premissas que devemos ter em mente:
  • os cinemas multiplex contemporâneos podem ter um ou mais auditórios dentro de um complexo maior,
  • cada auditório pode ter um número diferente de assentos,
  • os assentos são numerados com o número da fileira e a posição do assento dentro de uma fileira,
  • um filme pode ter várias exibições em horários diferentes ou pode ser exibido simultaneamente em um auditório diferente,
  • para cada exibição, um assento pode ser reservado/vendido apenas uma vez,
  • queremos rastrear quem inseriu cada reserva/venda no sistema.

Vejamos um possível projeto de banco de dados para resolver este problema (o modelo foi criado com Vertabelo para banco de dados MySQL):




As descrições curtas da estrutura da tabela são fornecidas abaixo:

  1. O movie tabela contém dados sobre os filmes que serão exibidos no cinema. A chave primária é id , que é auto_incremented como todas as chaves primárias em todas as outras tabelas. O único dado obrigatório é title .



    Todos os campos têm significados de acordo com seu nome. A coluna duration_min pode ser usado para desabilitar a inserção de uma nova exibição ou para mostrar uma mensagem de alerta caso queiramos entrar em uma exibição em um auditório onde a triagem anterior ainda está em andamento:
    previous screening start time + duration_min of it > this screening start time


  2. O auditorium tabela identifica todos os auditórios no teatro. Todos os dados são obrigatórios.



    O seats_no pode ser usado para calcular a porcentagem de disponibilidade de auditórios para uma exibição/filme/auditório/intervalo de data selecionados. Este é um exemplo de redundância de dados porque poderíamos obter o número de assentos para cada auditório contando-os no seat tabela. Neste exemplo, pode não melhorar significativamente o desempenho. Mostro aqui como uma ideia que pode ajudar no desenho de modelos mais complexos. Se configurarmos o banco de dados dessa maneira, devemos ter em mente que, se alterarmos um dado, também teremos que alterar outros. Se adicionarmos ou excluirmos dados do seat tabela temos que ajustar os valores seats_no no auditorium tabela.


  3. A screening tabela contém dados de todas as triagens e todos os campos são obrigatórios. Uma exibição deve ter um filme, auditório e hora de início relacionados. Não podemos ter duas apresentações no mesmo auditório ao mesmo tempo. Podemos definir uma chave única que consiste em auditorium_id e screening_start . Esta configuração é melhor do que definir uma chave única que consiste em movie_id , auditorium_id e screening_start porque isso nos permitiria entrar em exibições de dois filmes diferentes ao mesmo tempo no mesmo auditório.



    O código de visualização Vertabelo SQL para esta tabela se parece com isso (observe Screening_ak_1):

    -- Tables
    -- Table screening
    CREATE TABLE screening (
       id int    NOT NULL  AUTO_INCREMENT,
       movie_id int    NOT NULL ,
       auditorium_id int    NOT NULL ,
       screening_start timestamp    NOT NULL ,
       UNIQUE INDEX Screening_ak_1 (movie_id,auditorium_id,screening_start),
       CONSTRAINT Screening_pk PRIMARY KEY (id)
    );
    

  4. O seat tabela contém uma lista de todos os assentos que temos em auditórios com cada assento atribuído estritamente a um auditório. Todos os campos são obrigatórios.



  5. O reservation_type table é um dicionário de todos os tipos de reserva (por telefone, online, pessoalmente). Todos os campos são obrigatórios.



  6. O employee tabela lista todos os empregados que utilizam o sistema. Todos os campos são obrigatórios.



    Em sistemas complexos, geralmente há mais funções, portanto, precisamos ter um dicionário de funções e uma conexão funcionário/função de usuário. Em nosso exemplo temos apenas um papel:a mesma pessoa insere reservas e vende ingressos.


  7. A reservation e seat_reserved tabelas são as principais tabelas do nosso sistema. É por isso que eu os listei por último. Todas as outras tabelas podem existir sem tabelas de reserva, mas sem as tabelas de reserva perderíamos a razão de projetar todo o banco de dados em primeiro lugar.



    A reservation A tabela armazena dados sobre uma reserva e/ou venda de ingressos. Se tivermos uma reserva, o atributo reserved seria definido como True, o reservation_type_id seria definido de acordo com a origem da reserva e o employee_reserved_id conteria o id_employee valor da pessoa que inseriu os dados (estaria vazio se a reserva tivesse sido feita online pelo cliente). Da mesma forma, se os ingressos foram vendidos, o employee_paid_id seria preenchido com o id_employee valor da pessoa que vendeu os ingressos, o atributo pago seria definido como Verdadeiro. O atributo active identifica se um registro ainda é válido. Se os ingressos fossem vendidos, esse atributo sempre seria True e a reserva sem vendas ficaria ativa até 30 minutos antes do início da triagem



    O seat_reserved mesa nos permite fazer uma reserva ou um pagamento para vários lugares. Depois que o funcionário verifica alguns assentos livres na interface, um registro seria adicionado a essa tabela para cada um deles. Se quisermos verificar quais assentos estão livres ou ocupados, podemos verificar os valores nesta tabela associada à reservation tabela onde reservation.active = True .


Vale a pena mencionar:
  • employee_reserved_id não é obrigatório porque pode não existir reserva para um lugar (um bilhete para um lugar é vendido sem reserva prévia) ou é feito online
  • reservation_type_id é uma chave estrangeira que faz referência ao “id” do tipo de reserva. Não é obrigatório porque pode não existir uma reserva (caso tenhamos feito uma venda sem uma reserva prévia)
  • reservation_contact é um campo de entrada de texto para armazenar dados de uma pessoa que fez uma reserva, não é obrigatório porque uma reserva pode não existir (caso tenhamos feito uma venda sem uma reserva prévia)
  • employee_paid_id está relacionado a um usuário que fez uma venda, não é obrigatório porque uma venda pode não ter acontecido (assento foi reservado, a reserva foi cancelada automaticamente, o assento não foi vendido)
  • paid é um sinalizador que indica que o pagamento ocorreu e é obrigatório (os valores podem ser Sim/Verdadeiro ou Não/Falso)

No final, tenha em mente que ninguém gosta de encontrar outra pessoa em seu assento: