Mysql
 sql >> Base de Dados >  >> RDS >> Mysql

PHP MySQL Triggers - Como passar variáveis ​​para acionar?


Corrigir essa injeção de SQL
$username = mysql_real_escape_string($_POST['username']);
$password = mysql_real_escape_string($_POST['password']);
$sql = "INSERT INTO table1 VALUES ('username','password'); 
// You must quote your $vars       ^        ^ ^        ^  like this
// or syntax errors will occur and the escaping will not work!. 

Observe que armazenar senhas não criptografadas em um banco de dados é um pecado capital.
Veja abaixo como corrigir isso.

Os acionadores não permitem parâmetros
Você só pode acessar os valores que acabou de inserir na tabela.
O gatilho Insert tem uma tabela fictícia new para isso.
O gatilho Excluir tem uma tabela fictícia old para ver os valores que devem ser excluídos.
O acionador de atualização tem old e new .

Fora isso, você não pode acessar nenhum dado externo.
DELIMITER $$    

//Creates trigger to insert into table1 ( logs ) the userid and patientid ( which has to come from php )    

CREATE    
TRIGGER ai_table1_each AFTER INSERT ON `baemer_emr`.`table1`    
FOR EACH ROW    
BEGIN    
  INSERT INTO table2 VALUES (NEW.idn, NEW.username, NEW.patientid);    
END$$    

A solução
Crie uma tabela blackhole.
Tabelas blackhole para não armazenar nada, sua única razão de existir é para fins de replicação e assim você pode anexar triggers a elas.
CREATE TABLE bh_newusers (
  username varchar(255) not null,
  password varchar(255) not null,
  idn integer not null,
  patient_id integer not null,
  user_id integer not null) ENGINE = BLACKHOLE;

Em seguida, insira os dados na tabela blackhole e processe-os usando um gatilho.
CREATE    
TRIGGER ai_bh_newuser_each AFTER INSERT ON `baemer_emr`.bh_newuser
FOR EACH ROW    
BEGIN    
  DECLARE newsalt INTEGER;
  SET newsalt = FLOOR(RAND()*999999);
  INSERT INTO users (username, salt, passhash) 
    VALUES (NEW.username, newsalt, SHA2(CONCAT(newsalt, password), 512));
  INSERT INTO table2 VALUES (NEW.idn, NEW.username, NEW.patient_id);
END$$    

Observações sobre o gatilho
Você nunca deve armazenar senhas claras em um banco de dados.
Sempre armazene-as como um hash salgado usando a função de hash mais segura (atualmente SHA2 com um comprimento de chave de 512) , conforme mostrado no gatilho.
Você pode testar para ver se alguém tem a senha correta fazendo:
SELECT * FROM user 
WHERE username = '$username' AND passhash = SHA2(CONCAT(salt,'$password'),512)

Links
http://dev.mysql .com/doc/refman/5.0/en/blackhole-storage-engine.html
http://dev.mysql.com /doc/refman/5.0/en/create-trigger.html
Armazenando senhas com hash no MySQL
Como funciona a injeção de SQL das "Bobby Tables" Trabalho em quadrinhos do XKCD?