本文笔者使用Mysql5.6简单整理,数据库定时器、触发器、存储过程的使用
触发器是mysql5新增的功能,触发器和存储过程一样,都是嵌入到mysql的一段程序。(备注如果after触发器执行失败事务会回滚)
DROP TRIGGER IF EXISTS `trigger_data_section_satrt`;
DELIMITER ;;
CREATE TRIGGER `trigger_data_section_satrt` AFTER INSERT ON `tb_game_user_records` FOR EACH ROW begin
insert into tb_game_data_section (sysopenid,createtime,serno) value (new.sysopenid,new.createtime,new.serno);
end
;;
DELIMITER ;
以上为触发器创建代码“CREATE TRIGGER” 创建触发器 “trigger_data_section_satrt” 触发器名称 “ AFTER INSERT ON tb_game_user_records FOR EACH ROW” 在tb_game_user_records行插入值之后触发
主体以begin开始end结束
(。。。。看这里)old表示插入之前的值,new表示新插入的值 (看这里。。。。)
存储过程本人理解为声明的方法,此方法可无参或有参,可有返回值或无返回值,我们可以通过call sendCoupons(1,0,1);进行调用。SQL语句需要先编译然后执行,而存储过程(Stored Procedure)是一组为了完成特定功能的SQL语句集,经编译后存储在数据库中,用户通过指定存储过程的名字并给定参数(如果该存储过程带有参数)来调用执行它。
存储过程的编写,需了解一些基本语法比如”declare i int”;定义int类型属性i,”set @i=0;”给i设置初始值(PS属性声明时不要与参数重复且属性使用时需@属性名),另外还有if、while 、for等语法的使用。
-- ----------------------------
-- Procedure structure for `sendCoupons`
-- ----------------------------
DROP PROCEDURE IF EXISTS `sendCoupons`;
DELIMITER ;;
CREATE DEFINER=`fengrenjie`@`%` PROCEDURE `sendCoupons`(IN `lcstate` int,IN `lcstatecustom` int,IN `lctype` int)
BEGIN
#Routine body goes here...
DECLARE lid int;
declare i int;
#规则ID
DECLARE ctid int;
#本次派发劵总数量
declare lcount int;
#5元券应发放数量
DECLARE lcount1 int;
#10元券应发放数量
DECLARE lcount2 int;
#免单
DECLARE lcount3 int;
DECLARE lcount4 int;
DECLARE 1probability int;
set @i=0;
set @ctid=0;
set @lcount=0;
#set @lcount=()
SELECT id,probability,reward1,reward2,reward3 into @ctid,@1probability , @lcount1, @lcount2, @lcount3 from tb_game_coupons_type WHERE state>0 limit 1;
IF( @ctid>0) THEN
#set @ctid=(SELECT id from tb_game_coupons_type WHERE state=0 limit 1);
update tb_game_coupons_type SET state=state-1 where id=@ctid;
IF( lctype=1) THEN
set @lcount=@lcount1*@1probability/100;
END IF;
IF(lctype=2) THEN
set @lcount=@lcount2*@1probability/100;
END IF;
IF(lctype=3) THEN
set @lcount=@lcount3*@1probability/100;
END IF;
while @i<@lcount do
SET @lid= (SELECT min(id) as id from tb_game_coupons WHERE ctype=lctype and cstate =lcstatecustom);
if(lcstate> 0 ) THEN
update tb_game_coupons set cstate=lcstate, uptime = now() where id = @lid;
end if;
if(lcstate<0 ) THEN
update tb_game_coupons set cstate=lcstate,rptime = now() where id = @lid;
end if;
set @i=@i+1;
end while;
end if;
SELECT @ctid,@1probability , @lcount1, @lcount2, @lcount3,@lcount,@i ;
END
;;
DELIMITER ;
以上为笔者在时间项目中编写的存储过程(需求:有三种类型的卡款若干卡劵第一天发放70%第二天15%第三天15%)
tb_game_coupons_type 为发劵比例的配置表
CREATE DEFINER=fengrenjie
@%
PROCEDUREsendCoupons
(INlcstate
int,INlcstatecustom
int,INlctype
int)
DEFINER定义者,PROCEDUREsendCoupons
存储过程的名称(INlcstate
int,INlcstatecustom
int,INlctype
int)参数以及类型(备注字符串参数INlcstate
varchar(64)),
主体以begin开始end结束
自 MySQL5.1.6起,增加了一个非常有特色的功能–事件调度器(Event Scheduler),可以用做定时执行某些特定任务(例如:删除记录、对数据进行汇总等等),来取代原先只能由操作系统的计划任务来执行的工作。更值得 一提的是MySQL的事件调度器可以精确到每秒钟执行一个任务,而操作系统的计划任务(如:Linux下的CRON或Windows下的任务计划)只能精 确到每分钟执行一次。(以上定时器描述信息为借鉴)
-- ----------------------------
-- Event structure for `sendCouponsEvn`
-- ----------------------------
DROP EVENT IF EXISTS `sendCouponsEvn`;
DELIMITER ;;
CREATE DEFINER=`fengrenjie`@`%` EVENT `sendCouponsEvn` ON SCHEDULE EVERY 1 DAY STARTS '2018-06-06 23:59:59' ON COMPLETION NOT PRESERVE ENABLE DO
BEGIN
call sendCoupons(1,0,1);
call sendCoupons(1,0,2);
call sendCoupons(1,0,3);
END
;;
DELIMITER ;
可将一些数据库操作定时任务,从程序中挪到数据库中进行操作,可大大提升执行效率