Mapeamento com Doctrine no Symfony
Todo sistema tem um momento em que a estrutura das coisas já esta bem definida e, normalmente, é aí que começamos a expansão.
Nesse momento é legal ter bastante cuidado e garantir que tudo está bem alinhado pois o processo pode ser bem repetitivo.
Relacionando entidades
Nosso sistema TikTok® já tem uma entidade, com um front-end em Bootstrap bem isolado, mas ainda faltam duas entidades bem importantes: HoraLancada e Projeto.
Seguindo os conceitos de modelagem citados quando criamos a classe Funcionario, precisamos saber o que uma HoraLancada e Projeto tem e fazem
Projeto
Em um sistema de gestão de horas, Projeto precisa ter um nome, funcionários que atuam naquele projeto e fazer o calculo do total de horas dedicadas neste projeto.
Relacionando Entidades
Aqui temos um ponto crucial. Se um Projeto tem muitos Funcionarios, precisamos representar esse relacionamento na nossa classe Projeto:
Perfeito, temos um atributo para guardar esses funcionários. Mas, como fazer esse relacionamento no banco de dados? Ou seja, como vamos falar pro Doctrine que precisamos aquilo representa uma coleção de funcionários?
Mapeando entidades
Da mesma forma que dizemos para o doctrine com anotações quem era o Id, o tipo dele, podemos dizer para qual entidade esse atributo funcionários aponta. Além disso, também podemos dizer se um projeto tem muitos funcionários (OneToMany) e quem representa o outro lado desse mapeamento, ou seja, qual atributo guarda o projeto de cada funcionário:
O outro lado
Perfeito, já falamos certinho qual é a entidade que está relacionada ao atributo funcionários e até apontamos quem vai guardar o projeto dentro de cada Funcionario.
Mas, precisamos criar efetivamente essa representação em Funcionário e dizer que todo funcionário tem um Projeto. E mais, precisamos indicar que muitos funcionários estão dentro de um projeto(ManyToOne) indicando a classe de destino e quem vai guardar esses funcionários lá dentro:
Para garantir que nosso mapeamento está certinho, podemos utilizar o comando do Symfony:
php bin/console doctrine:schema:validate
Outros Mapeamentos
Além desse tipo de mapeamento, temos muitos outros, como ManyToMany e OneToOne, bidirecionais e uni-direcionais. Cada caso é um caso e o melhor lugar para consultar o jeito certo de se fazer esses mapeamentos é olhando a documentação do Doctrine.
HoraLancada
Da mesma forma que um projeto tem muitos funcionários, um funcionário tem muitas HoraLancada. Ou seja, temos, de novo, um OneToMany de funcionário para HoraLancada e ManyToOne de HoraLancada para funcionário.
A mesma ideia se repete quando pensamos que todo projeto tem um total de horas lançadas! Ou seja, de novo, um Projeto tem muitas HoraLancada e uma HoraLancada está em um projeto. Mais uma vez, OneToMany.
Além disso, uma HoraLancada deve ter uma descrição, o que o funcionário fez e em quanto tempo ele gastou, em horas e minutos:
O outro lado
Da mesma forma que fizemos para Funcionario, agora precisamos fazer para HoraLancada. Já temos todo o mapeamento da HoraLancada mas falta indicar esse mapeamento nas entidades Funcionario e Projeto.
Validando novamente nosso mapeamento com o comando:
Sabemos que está tudo certo =)
E, finalmente, para aplicar as mudanças no banco, rodamos o comando:
php bin/console doctrine:schema:update -f
Próximos passos
Agora que temos todas as entidades relacionadas, o próximo desafio (e final) será realizar as funcionalidades de Adição, Remoção, Listagem e Edição (mais conhecido como CRUD) das nossas entidades relacionadas. Para isso, vamos utilizar o FormType do symfony =)
E vocês, o que acharam do relacionamento entre entidades com o Doctrine + Symfony?