VueJS - Many to Many
[Finalizado Pelo Aluno]
Tenho um modal em vuejs onde eu realizo o cadastro de pessoa, nesse cadastro tem algumas informações que são de n-n e para isso eu usei checkbox para realizar o insert. Até aí OK.
Só que estou tendo dificuldade em fazer o update desse cadastro, pois estou utiizando o mesmo modal para o update. A minha dúvida é qual a melhor forma de tratar essa situação? Sendo que toda vez que o usuário marcar ou desmarcar algum check, o mesmo terá que ser adicionado/removido da tabela pivot
Para exemplificar melhor o problema:
Na parte de cadastro eu tenho a seguinte estrutura em html
HTML:
______________________________________________________
<div class="col-sm-6" v-for="(value, key, index) in problemas" :key="index">
<div class="form-group">
<div class="custom-control custom-checkbox">
<input class="custom-control-input" type="checkbox" :id="value.id" :value="value.id" v-model="form.checked_problemas" />
<label :for="value.id" class="custom-control-label">{{value.descricao}}</label>
</div>
</div>
</div>
________________________________
e no script eu declarei uma array:
Para inserir, ela é populada da seguinte forma:
checked_problemas:[4,6,8]
Então eu consigo fazer o insert na tabela pivot
_____________________________
Agora para alterar que é o problema, pois quando carrego o modal para editar a variavel que deveria ser uma array fica:
e quando marco ou desmarco algum, todos os checks vinculados no v-model são marcados ou desmarcados pois o valor retornado é true ou false
Qual a melhor maneira de trazer esses dados preenchidos e depois realizar o update? Pois os campos que serem desmarcados vão precisar ser excluidos da tabela pivot
PS: desculpa a má formatação, não consegui entender como identa
Olá, Rafael!
Tudo bem?
Nesse caso recomendo que no backend (API) você utilize o método sync, porque toda vez que receber os dados do formulário basta sincronizar com o banco de dados, e tudo ok; (https://laravel.com/docs/6.x/eloquent-relationships#updating-many-to-many-relationships)
Já no frontend deve usar o two-way-databind (acredito que aqui está ok, certo?)
Show, não sabia dessa dica do laravel. Vou dar uma olhada...
no front end estou tendo problema para popular a variavel checked, como eu faria isso?
Tem esse código no GitHub, para eu poder dá uma olhada e analisar onde você está errando?
Quando tento editar o registro, não estou conseguindo popular os checboxes como marcado. A minha API retorna o seguinte objeto:
[
-
-
id: 1,
-
descricao: "Aquisição de Matéria Prima",
-
created_at: "2020-01-14 14:18:29",
-
updated_at: "2020-01-14 14:18:29",
-
pivot:
-
artesao_id: 1,
-
problema_id: 1
-
-
-
-
id: 2,
-
descricao: "Embalagem",
-
created_at: "2020-01-14 14:18:29",
-
updated_at: "2020-01-14 14:18:29",
-
pivot:
-
artesao_id: 1,
-
problema_id: 2
-
-
]
No HTML eu uso o mesmo modal para inserção/edição e está da seguinte forma:
Como eu consigo trazer esses valores marcados de acordo com o resultado da api?
É possível fazer o two-way-databind com os dados retornados da API.
Outra alternativa (talvez seja mais simples) é criar um método (ou propriedade computada) que retorna true ou fase, exemplo:
// Checkbox
<input
class="custom-control-input"
type="checkbox"
:id="value.id"
:value="value.id"
v-model="form.checked_problemas"
:checked="hasSelected(value.id)"
:/>
// Método
hasSelected (id) {
const problemasAtuais = this.problemas
const problema = problemasAtuais.find(problema => problema.id == id);
// retorna true caso exista, caso contrário retorna false
return problema !== undefined;
}
Faça ao teste, fiz apenas de cabeça.
Fiz dessa maneira no html:
e no computed:
porém, está dando esse erro e não funciona:
vue.common.dev.js?4650:630 [Vue warn]: Error in render: "TypeError: _vm.hasSelected is not a function"
found in
---> <Artesoes> at resources/js/components/Artesoes.vue
<Root>
Olá amigo!
Deixe o hasSelected como método, declare em mehtods: {...}
No aguardo.
Coloquei dessa maneira, e o erro parou de acontecer.
Porém, quando eu abro o modal para editar a variavel checked_problemas está como undefined, deveria vim uma array com os valores marcados, correto?
E quando eu marco algum check, ela muda o valor para true, marcando todos os grupos de checbox
Olá amigo!
A propriedade "problemasAtuais" deve conter apenas os problemas que foram vinculados (N:N);
Nesse component você precisa ter uma propriedade com apenas os valores selecionados, pois é baseado nesses valores que vamos validar para o checkbox vir marcado ou não.
Exemplo com JS puro (testado):
const problemas = [
{id: 1, name: 'pro1'},
{id: 2, name: 'pro2'},
{id: 3, name: 'pro3'},
{id: 4, name: 'pro4'},
{id: 5, name: 'pro5'},
]
// Dados que foram inseridos antes (N:N)
const problemasAtuais = [
{id: 1, name: 'pro1'},
{id: 4, name: 'pro4'},
{id: 3, name: 'pro4'},
]
function hasSelectedProblemas(id) {
const problema = problemasAtuais.find(problema => problema.id == id);
return problema !== undefined;
}
console.log(hasSelectedProblemas(1))
Beleza, professor. fiz as alterações e o problema continua devido ao v-model, acredito... nunca pensei que fosse dar tanta dificuldade rss
Mesmo fazendo essas alterações, o v-model fica como undefined, como eu consigo fazer com que ela receba um array? Pois quando inspeciono o elemento e coloco a array na mão, os valores na tela são preenchidos e só falta isso para completar o crud
0:
id: 1
descricao: "Aquisição de Matéria Prima"
created_at: "2020-01-14 14:18:29"
updated_at: "2020-01-14 14:18:29"
1:
id: 2
descricao: "Divulgação"
created_at: "2020-01-14 14:18:29"
updated_at: "2020-01-14 14:18:29"
quando eu adiciono a array na mão, o formulário é preenchido corretamente:
Como eu consigo transformar esse objeto em uma array desse tipo? Acredito que resolvendo isso, acaba o problema
Na verdade nem sei mais, to perdido... eu fiz o seguinte teste
Na teoria, deveria imprimir o array, certo? Só que o resultado é esse:
[__ob__: Observer]
length: 0
__ob__: Observer {value: Array(0), dep: Dep, vmCount: 0}
__proto__: Array
Você tem esse código no GitHub, para eu poder dá uma olhada e analisar onde você está errando?
https://bitbucket.org/rafaellannes/debug
A rota /register tá funcionando e eu coloquei o arquivo sql do banco pra poupar tempo.
O arquivo em questão é o Artesoes.vue. Na primeira aba tem os check's, infelizmente não consegui avançar mto. Eu estava realizando testes no método EditModal, pois ali tenho o objeto completo com todos os dados, mas testei várias soluções e não consegui avançar.
Obrigado pela ajuda
https://bitbucket.org/rafaellannes/debug/src/master/
(coloquei o link em cima tb, mas ficou invisivel devido a formatação)
Olá, Rafael!
Esse bug tá em qual component mesmo?
Precisa estar logado para conseguir responder a este ticket!
Clique Aqui Para Entrar!