本例子是基于mybits+mysql的存储过程实例
service类
@Override
public void profitMargin(String docOrderNo,String pmId) {
try {
Map maps = new HashMap();
maps.put("pDocOrderNo", docOrderNo);
maps.put("pmId", pmId);
tOrderDocumentDao.profitMargin(maps);
}catch(Exception e) {
e.printStackTrace();
}
}
dao类
/*
* 计算利润率
*/
void profitMargin(Map map);
mapping类
BEGIN
DECLARE interpreterTotalPrice DECIMAL(10,2) DEFAULT 0.00;
DECLARE r_profit_margin VARCHAR(20);
-- 查找baseOrderNo
SELECT IFNULL(t1.`p_order_no`,IFNULL(t1.`order_no`,IFNULL(t.`p_order_no`,t.order_no))) INTO @baseOrderNo FROM `t_order_document` t LEFT JOIN t_order_document t1 ON t1.`id` = t.p_id
WHERE t.`order_no` = p_doc_order_no;
-- 订单价格
SELECT real_price,cost_price INTO @baserealPrice,@baseCostPirce FROM t_order_base WHERE order_no = @baseOrderNo;
-- 加价
SELECT IFNULL(SUM(fee),0) INTO @fee FROM `t_order_fee_add` WHERE order_no = @baseOrderNo;
-- 译员总价格
-- 查找所有子订单的orderNO
SELECT GROUP_CONCAT(CONCAT('\'',order_no,'\'')) INTO @docOrderNos FROM t_order_document WHERE order_no = p_doc_order_no;
-- 拼接sql
SET @sql = CONCAT('SELECT SUM(cost_price) INTO @interpreterTotalPrice FROM t_order_document_link WHERE order_no IN (',@docOrderNos,') and del_state = \'1\'');
-- 执行
PREPARE stmt FROM @sql;
EXECUTE stmt;
SET interpreterTotalPrice = @interpreterTotalPrice;
DEALLOCATE PREPARE stmt;
SET r_profit_margin = ROUND((1-ROUND(interpreterTotalPrice/@baserealPrice,4))*100,2);
-- 修改base表利润率
UPDATE t_order_base SET total_profit_margin = r_profit_margin , total_cost = interpreterTotalPrice WHERE order_no = @baseOrderNo;
-- 修改当前子订单的利润率
SELECT SUM(cost_price) INTO interpreterTotalPrice FROM t_order_document_link WHERE order_no = p_doc_order_no AND del_state = '1';
SELECT real_price INTO @docRealPrice FROM t_order_document WHERE order_no = p_doc_order_no;
SET @docRealPrice = @docRealPrice + (@docRealPrice/@baseCostPirce) * @fee;
SET r_profit_margin = ROUND((1-ROUND(interpreterTotalPrice/@docRealPrice,4))*100,2);
UPDATE
t_order_document_link
SET
profit_margin = r_profit_margin
WHERE order_no = p_doc_order_no
AND create_user = pm_id
AND cir_tag IS NOT NULL
ORDER BY create_time DESC
LIMIT 1 ;
END
SQL总结(五)存储过程
http://www.cnblogs.com/yank/p/4235609.html
如下是另一个存储过程(未使用)
BEGIN
DECLARE done INT DEFAULT 0; -- 循环标识
DECLARE interpreterTotalPrice DECIMAL(10,2) DEFAULT 0.00; -- 译员总价格
DECLARE refundFee DECIMAL(10,2) DEFAULT 0.00; -- 退款数额
DECLARE r_profit_margin VARCHAR(20); -- 利润率
DECLARE linkId VARCHAR(50) DEFAULT ''; -- 环节总表Id
DECLARE createTime TIMESTAMP; -- 环节总表创建时间
DECLARE docId VARCHAR(36); -- 文档表id
DECLARE docOrderNo VARCHAR(36); -- 文档表no
DECLARE docRealPrice DECIMAL(10,2) DEFAULT 0.00; -- 文档价格
DECLARE docOrderNos VARCHAR(200) DEFAULT ''; -- 文档编号集合,使用逗号隔开
DECLARE multilingual_record CURSOR FOR SELECT id,order_no,real_price FROM `t_order_document` WHERE del_state = '1' AND p_order_no = p_base_order_no; -- 多语言文档游标
DECLARE cur CURSOR FOR(SELECT id,create_time FROM doclink_view); -- 视图表
DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = 1;
-- 获取主订单总价格
-- 订单价格
SELECT real_price INTO @realPrice FROM t_order_base WHERE order_no = p_base_order_no;
-- 加价
SELECT IFNULL(SUM(fee),0) INTO @fee FROM `t_order_fee_add` WHERE order_no = p_base_order_no;
-- 补差价
SELECT IFNULL(SUM(cost_price),0) INTO @priceDifferences FROM `t_order_base` WHERE order_no LIKE CONCAT('%',p_base_order_no,'-BXJ%') AND del_state = '1' AND pay_type IS NOT NULL;
SELECT COUNT(1) INTO @countFlag FROM t_order_document WHERE order_no = p_base_order_no AND del_state = '1';
IF @countFlag <> 0 THEN -- 单语言
-- 计算base表的利润率
-- 查询退款信息
SELECT IFNULL(SUM(fee),0) INTO refundFee FROM `t_order_proc_refund` WHERE audit_state = '1' AND del_state = '1' AND order_no = p_base_order_no;
SET @sumPrice = @realPrice + @fee + @priceDifferences - refundFee;
-- 计算总订单的利润率
SELECT SUM(cost_price) INTO interpreterTotalPrice FROM t_order_document_link WHERE order_no = p_base_order_no AND del_state = '1';
SET r_profit_margin = ROUND((1-ROUND(interpreterTotalPrice/@sumPrice,4))*100,2);
-- 修改base表利润率
UPDATE t_order_base SET total_profit_margin = r_profit_margin , total_cost = interpreterTotalPrice WHERE order_no = p_base_order_no;
-- MySQL本身是不支持动态游标的,但可以通过(准备语句+视图+静态游标)的方法来近似实现。
DROP VIEW IF EXISTS doclink_view;
SET @sqlstr = CONCAT('CREATE VIEW doclink_view AS SELECT id, create_time FROM t_order_document_link WHERE order_no = \'',p_base_order_no,'\' AND del_state = \'1\' AND cost_price IS NOT NULL');
PREPARE stmt FROM @sqlstr;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;
OPEN cur;
f_loop:LOOP FETCH cur INTO linkId,createTime;
IF done THEN
LEAVE f_loop;
END IF;
SELECT IFNULL(SUM(cost_price),0) INTO @docCostPrice FROM t_order_document_link WHERE order_no = p_base_order_no AND create_time <= createTime;
-- 修改doc利润率
SET r_profit_margin = ROUND((1-ROUND( @docCostPrice/@sumPrice,4))*100,2);
UPDATE t_order_document_link SET profit_margin = r_profit_margin WHERE id = linkId;
END LOOP f_loop;
CLOSE cur;
ELSE -- 多语言
OPEN multilingual_record;
f_loop:LOOP FETCH multilingual_record INTO docId,docOrderNo,docRealPrice;
SELECT docId;
IF done THEN
LEAVE f_loop;
END IF;
IF docOrderNos = '' THEN
SET docOrderNos = CONCAT('\'',docOrderNo,'\'');
ELSE
SET docOrderNos = CONCAT(docOrderNos,',\'',docOrderNo,'\'');
END IF;
-- 查询退款信息
SELECT IFNULL(SUM(fee),0) INTO @refundFee FROM `t_order_proc_refund` WHERE audit_state = '1' AND del_state = '1' AND order_no = docOrderNo;
SET refundFee = refundFee + @refundFee;
SET docRealPrice = docRealPrice - @refundFee + (docRealPrice/@realPrice) * (@fee + @priceDifferences);
DROP VIEW IF EXISTS doclink_view;
SET @sqlstr = CONCAT('CREATE VIEW doclink_view AS SELECT id,create_time FROM t_order_document_link WHERE order_no = \'',docOrderNo,'\' AND del_state = \'1\' AND cost_price IS NOT NULL');
PREPARE stmt FROM @sqlstr;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;
OPEN cur;
myLoop:LOOP FETCH cur INTO linkId,createTime;
IF done THEN
LEAVE myLoop;
END IF;
SELECT SUM(cost_price) INTO @docCostPrice FROM t_order_document_link WHERE order_no = docOrderNo AND create_time <= createTime;
-- 修改doc利润率
SET r_profit_margin = ROUND((1-ROUND(@docCostPrice/docRealPrice,4))*100,2);
UPDATE t_order_document_link SET profit_margin = r_profit_margin WHERE id = linkId;
END LOOP myLoop;
CLOSE cur;
SET done = 0;
END LOOP f_loop;
CLOSE multilingual_record;
SET @sumPrice = @realPrice + @fee + @priceDifferences - refundFee;
-- 计算总订单的利润率
SET @sqlstr = CONCAT('SELECT SUM(cost_price) INTO interpreterTotalPrice FROM t_order_document_link WHERE order_no IN (',docOrderNos,') AND del_state = \'1\'');
SET r_profit_margin = ROUND((1-ROUND(interpreterTotalPrice/@sumPrice,4))*100,2);
-- 修改base表利润率
UPDATE t_order_base SET total_profit_margin = r_profit_margin , total_cost = interpreterTotalPrice WHERE order_no = p_base_order_no;
END IF;
END