Erro criando trigger

Olá,

Alguém poderia me auxiliar em um pedaço de código pra inserir dados no banco de dados usando trigger? Estou aprendendo triggers agora para um sistema mais complexo que farei em seguida mas estou com um pouco de dúvida e o código aparentemente está funcionando normalmente, mas não está inserindo o valor ‘30’ no banco de dados.

Imagem do código com a trigger:

Código:

$query_fundaPrimeiraCidadeUsuario = “INSERT INTO cidade(idCidade, nomeCidade, idUsuario, turnos)
VALUES(NULL,’$nomeCidade’,’$idUsuario’, 0)”;

$resultado_fundaPrimeiraCidadeUsuario = mysqli_query($conexao,$query_fundaPrimeiraCidadeUsuario);

$query_idRecemInserido = “SELECT LAST_INSERT_ID();”;
$resultado_idRecemInserido = mysqli_query($conexao,$query_idRecemInserido);

$row_resultado_idRecemInserido = mysqli_fetch_array($resultado_idRecemInserido);

echo $row_resultado_idRecemInserido;

$query_CriacaoTurnoCidade = “CREATE TRIGGER iniciaContagemTurno AFTER INSERT
ON cidade
FOR EACH ROW
BEGIN
/corpo do código/
UPDATE cidade SET turnos = (turnos + 30) WHERE ‘idCidade’ = ‘$row_resultado_idRecemInserido’;
END”;

Resumindo, criei uma trigger que gostaria que inserisse o valor ‘30’ no campo ‘turnos’ da tabela ‘cidade’.

Aparentemente funciona pois não está retornando erro na tela, porém também não está inserindo o valor no campo da tabela.

Estou procurando o ‘erro’ mas se alguém mais experiente bater o olho e souber onde está o ‘erro’ e quiser ajudar eu agradeço.

Obrigado.

Me parece que você está confundindo como uma trigger funciona. Você nao precisa (ou deveria) criar a trigger quando está inserindo o registro. A trigger é conectada a tabela e entrará em açao toda vez que a açao específica (delete, insert, update) for executada naquela tabela.

O que você deseja fazer exatamente nesse exemplo?

Aliás, um conselho que dou é evitar triggers para regras de negócio. Parecem ser recursos ótimos mas causam várias dores de cabeça no dia a dia:

  • Pessoas novas no código nao conseguem encontrar onde aquele comportamento está sendo executado
  • Controle de versao e deploy costuma ser mais bagunçado, se nao fizer um esforço extra.
  • Testes também nao sao tao triviais de escrever.

Enfim, é legal aprender e ver como funciona, mas se vai escrever um sistema mais complexo, recomendo que use recursos mais simples.

Olá @AbelBueno,

Obrigado pela resposta.

A trigger é conectada a tabela e entrará em açao toda vez que a açao específica (delete, insert, update) for executada naquela tabela.

Está aí algo que eu preciso fazer em seguida depois de conseguir saber como funciona.

Minha intenção é criar um ‘sistema de turnos’ para um jogo web browser. A idéia é bem simples. Um contador conta até 60 segundos e adiciona 3 turnos no campo ‘turno’. Mas ainda não comecei a implementar esse código e pra falar a verdade, nem sei se tem como. Mas fazer um sistema de turnos como o que eu falei é possível, que já vi em jogos no mesmo estilo que estou tentando criar. Sei que tem como, só não sei fazer ainda.

Como você disse, e eu percebi um pouco de relance, é que eu poderia inserir os dados do turno diretamente na query do PHP/MySQL. Porém pra fazer o sistema de contador que adiciona os turnos na tabela, eu preciso da trigger.

Tem alguma idéia de como posso fazer isso com triggers no MySQL? Sugestão de funções de tempo em SQL, por exemplo, pra fazer um contador na trigger?

Quanto ao código deste tópico, travei justamente no código da trigger mesmo. Não estou conseguindo passar o ultimo registro “LAST_INSERT_ID()” pra trigger funcionar e adicionar os turnos no banco de dados:

$query_CriacaoTurnoCidade = “CREATE TRIGGER iniciaContagemTurno AFTER INSERT
ON cidade
FOR EACH ROW
BEGIN
/corpo do código/
UPDATE cidade SET turnos = (turnos + 30) WHERE idCidade =’”.$row_resultado_idRecemInserido[0]."’;
END";

Obrigado pela ajuda.

Ainda não consegui fazer a trigger funcionar. Tentei fazer manualmente no PHPMYADMIN mas como eu esperava também deu erro.

O objetivo é apenas inserir o valor 30 no campo ‘turnos’ da tabela ‘cidade’.

Imagem da tentativa manual:

Alguém sabe como fazer essa trigger funcionar?

Obrigado por qualquer ajuda.

Entao, me parece que você quer invocar a trigger automaticamente a cada X segundos, nao é para isso que existe triggers. Elas respondem a um evento. Esse timer é provavelmente mais fácil de implementar direto na sua aplicaçao.

Um exemplo da trigger que você quer fazer, seria assim:

delimiter /

create table cidades (
  id_cidade int primary key,
  turnos int
)
/

CREATE TRIGGER cidades_before_insert
BEFORE INSERT ON cidades
FOR EACH ROW 
BEGIN
   SET new.turnos = new.turnos + 30;
END;
/

insert into cidades(id_cidade, turnos) values(1, 0)
/
insert into cidades(id_cidade, turnos) values(2, 10)
/
select * from cidades;

https://www.db-fiddle.com/f/ifJnnTr5wB8x8ayssLhojv/0

O comando set, no mysql, vai dizer que o valor da coluna turnos para o registro sendo inserido new tem que ser o valor passado na query + 30.

Repare que o id_cidade nao é necessário nesse caso, mas se precisasse usar, você chamaria new.id_cidade, pois você nao terá o valor id_cidade = 30 nessa hora.

1 curtida

Realmente estou precisando de ajuda. Muito obrigado pela ajuda.

Fiz já mais de 120 tentativas de tudo que é jeito e não consigo alterar o campo “turnos”. Ele permaneceu inalterado até agora com o valor zero(‘0’).

Código no Pastebin:
https://pastebin.com/RQS4UXE6

Alguma ajuda pra esse código inserir os dados no campo?

Muito obrigado por sua ajuda.

— EDIT —

Uma coisa que notei é que você faz os inserts DEPOIS da trigger? Tentei também invertendo mas só a trigger é processada mas não deixa inserir dados no banco de dados.

Olha só, vamos lá:

  • Primeiro, retire esse código do PHP, a trigger é criada antes da sua aplicaçao começar a rodar.
  • Para manipular os valores sendo inseridos, você usa o comando SET que coloquei de exemplo, nao um UPDATE como está fazendo (senao terá o erro que colocou no outro post que criou)
  • Também, para manipular os valores sendo inseridos, a trigger tem que ser BEFORE INSERT e nao AFTER INSERT
  • Sim, o insert vem depois da trigger, pois como disse, a trigger reage a eventos. Se você criar a trigger depois do insert, o evento já ocorreu, e ela nao vai fazer nada.
  • No exemplo que passei, a parte de insert e select ficariam na sua aplicaçao. O comando para criar a trigger você executa antes de tudo isso.

Tenta seguir esses passos e veja se funciona.

1 curtida

Hahaha…e não é que funcionou mesmo?

Obrigado pela ajuda.

  • Criei o SQL da trigger diretamente no PHPMYADMIN.

  • Tirei o UPDATE que tinha visto em outros exemplos na internet.

  • E realmente, o PHPMYADMIN nem aceitou o AFTER INSERT. Só aceitou rodar o script utilizando BEFORE INSERT.

Agora está funcionando. O campo foi atualizado.

Muito obrigado @AbelBueno.