2012-08-13 14 views
7

hola tengo una base de datos con muchas mesas y las claves externas como estaMysql gatillo bucle de resultado de la consulta con muchas filas

CREATE TABLE IF NOT EXISTS `articulos` (
    `id` int(11) NOT NULL AUTO_INCREMENT, 
    `nombre` varchar(63) NOT NULL, 
    `contenido` text NOT NULL, 
    `normas_id` int(11) NOT NULL, 
    PRIMARY KEY (`id`) 
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=138 ; 

CREATE TABLE IF NOT EXISTS `aspectosambientales` (
    `id` int(11) NOT NULL AUTO_INCREMENT, 
    `nombre` varchar(63) NOT NULL, 
    PRIMARY KEY (`id`) 
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=28 ; 

CREATE TABLE IF NOT EXISTS `aspectosambientales_articulos` (
    `id` int(11) NOT NULL AUTO_INCREMENT, 
    `aspectosambientales_id` int(11) NOT NULL, 
    `articulos_id` int(11) NOT NULL, 
    PRIMARY KEY (`id`), 
    KEY `fk_aspaspectosambientales1`  (`aspectosambientales_id`), 
    KEY `fk_aspee` (`articulos_id`) 
) ENGINE=InnoDB DEFAULT CHARSET=utf8 UTO_INCREMENT=225 ; 

CREATE TABLE IF NOT EXISTS `empresas` (
    `id` int(11) NOT NULL AUTO_INCREMENT, 
    `razonsocial` varchar(127) DEFAULT NULL, 
    `nit` varchar(63) DEFAULT NULL, 
    `direccion` varchar(127) DEFAULT NULL, 
    `telefono` varchar(15) DEFAULT NULL, 
    `web` varchar(63) DEFAULT NULL, 
    `auth_user_id` int(11) NOT NULL, 
    PRIMARY KEY (`id`) 
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=2 ; 

CREATE TABLE IF NOT EXISTS `articulos_empresas` (
    `id` int(11) NOT NULL AUTO_INCREMENT, 
    `empresas_id` int(11) NOT NULL, 
    `articulo_id` int(11) NOT NULL, 
    `acciones` text, 
    `responsable` varchar(255) DEFAULT NULL, 
    `plazo` date DEFAULT NULL, 
    `cumplido` tinyint(1) DEFAULT NULL, 
    PRIMARY KEY (`id`), 
    KEY `fk_normas_empresas_empresas1` (`empresas_id`), 
    KEY `fk_normas_empresas_normas1` (`normas_id`) 
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ; 

y necesito crear un disparador para llenar los 'articulos_empresas' después de la inserción en 'empresas 'para todas las filas en' articulos 'que coinciden con' aspectosambientals 'que las nuevas' empresas 'seleccionaron.

recibo de todos los articulos 'con esta consulta

SELECT articulos_id FROM aspectosambientales_articulos 
    WHERE aspectosambientales_id = ID 
     -- ID is the aspectosambientales_id selected when the 'empresas' row is created 
     -- maybe something like NEW.aspectosambientales_id 

pero no sé cómo crear un bucle como 'bucle' en el disparador para cada resultado en la consulta

algunos como este:

CREATE TRIGGER 'filltableae' AFTER INSERT ON 'empresas' 
FOR EACH ROW 
BEGIN 
DECLARE arrayresult = (SELECT articulos_id FROM aspectosambientales_articulos 
    WHERE aspectosambientales_id = NEW.aspectosambientales_id) 
--- here is when i have to do the loop for all the results 
--- for ids in arrayresults 
--- insert into articulos_empresas ('',NEW.id, ids, '', '' ,'','') 
--- endfor 
END 

gracias !!!

Respuesta

8

Por lo que sé, puede repetir el resultado de una consulta SELECT utilizando cursores. Ver aquí: http://dev.mysql.com/doc/refman/5.0/en/cursors.html

+0

Funciona, y si guardo ir como un procedimiento, puedo enviar el NEW.id como un param del procedimiento si es necesario usarlo en otros desencadenantes – elin3t

+0

Basado en @Razvan respuesta dejé el resultado aquí: – elin3t

28

Basado en respuesta @Razvan me fui de aquí el código para el gatillo, así que tal vez puede ayudar a alguien

DROP TRIGGER IF EXISTS AEINST; 
DELIMITER // 
CREATE TRIGGER AEINST AFTER INSERT ON procesos_aspectos 
FOR EACH ROW 
BEGIN 
    DECLARE done INT DEFAULT FALSE; 
    DECLARE ids INT; 
    DECLARE cur CURSOR FOR SELECT articulos_id FROM aspectosambientales_articulos WHERE aspectosambientales_id = NEW.aspectosambientales_id; 
    DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = TRUE; 

    OPEN cur; 
     ins_loop: LOOP 
      FETCH cur INTO ids; 
      IF done THEN 
       LEAVE ins_loop; 
      END IF; 
      INSERT INTO articulos_empresas VALUES (null,ids, NEW.empresas_id,null,null,null,null); 
     END LOOP; 
    CLOSE cur; 
END; // 
DELIMITER ; 

gracias de nuevo!

+0

Gran respuesta , muy útil en producción y prácticas. –

Cuestiones relacionadas