oracle - 如何解决突变触发器
问题描述
我是 PL / SQL ORACLE 的新手 我有一个问题,要触发一个变异表
我想实现以下几点:通过在 ORDER_ITEMS 表中插入订单,订购的数量(数量)保留在表库存(QUANTITY_ON_HAND)的库存中
TABLE ORDER_ITEMS
-ORDER_ID
-PRODUCT_ID-
-UNIT_PRICE
-QUANTITY
键是 ORDER_ID 并按序列增加
THE TABLE INVENTORIES
-PRODUCT_ID
-WHAREHOUSE_ID
-QUANTITY_ON_HAND
我已经执行了获得 PRODUCT_ID 和插入到表 ORDER_ITEMS 中的最后一条记录的订购量的功能
CREATE OR REPLACE FUNCTION get_data__order_quantity
RETURN number IS
quantity_order number;
BEGIN
select quantity into quantity_order from (select * from ORDER_ITEMS order by order_id desc) where rownum=1;
RETURN quantity_order ;
END get_data__order_quantity;
CREATE OR REPLACE FUNCTION get_data_cod_prod
RETURN number IS
cod_producto number;
BEGIN
select product_id into cod_producto from (select * from ORDER_ITEMS order by order_id desc) where rownum=1;
RETURN cod_producto ;
END get_data_cod_prod;
我已经执行了这个表格的触发
create or replace trigger actualizar_stock
after insert --AFTER INSERT
on ORDER_ITEMS -- ON TABLE ORDER_ITEMS
for each row
declare
ctn_ordenada int; --STORE THE AMOUNT OF ORDERED PRODUCTS
cod_produc int; --STORE THE ID OF THE PRODUCT THAT HAS BEEN ORDERED
id_wharehouse int; --STORE THE ID OF THE FIRST WAREHOUSE ENCOUNTERED WITH THE PRODUCT IN EXISTENCE
stock_bodega int; --STORE THE EXISTENCE OF PRODUCTS (STOCK) IN BODEGA
begin
ctn_ordenada:=get_data__order_quantity; --THE AMOUNT ORDERED FROM THE FUNCTION IS ASSIGNED
cod_produc :=get_data_cod_prod; -- THE PRODUCT ID IS ASSIGNED FROM THE FUNCTION
select quantity_on_hand into stock_bodega from inventories where (quantity_on_hand > 0 and rownum=1 and product_id=cod_produc); -- SE ASIGNA EL STOCK
select wharehouse_id into id_wharehouse from inventories where (quantity_on_hand > 0 and rownum=1 and product_id=cod_produc); -- THE ID OF THE WAREHOUSE IS ASSIGNED
-- IF THE ESTOCK IS GREATER THAN 0
if (stock_bodega >0) then
begin
--UPDATE (REST THE CURRENT VALUE WITH THE ORDERED AMOUNT)
update inventories set quantity_on_hand=quantity_on_hand-ctn_ordenada where wharehouse_id=id_wharehouse;
end;
else
begin
-- DO NOT UPDATE
dbms_output.put_line('Registration not updated');
end;
end if;
end;
-- END OF THE TRIGGER
请帮忙
解决方案
基本问题是从触发器调用的函数get_data__order_quantity
和get_data_cod_prod
访问定义触发器的表。这将导致变异表异常。
当然,另一个问题是您的函数很可能不会按照您的意图进行。您说“我已经执行了获得 PRODUCT_ID 和在表格 ORDER_ITEMS 中插入的最后一条记录的订购量的功能”,但您的选择标准是...WHERE ROWNUM = 1
。没有办法提前知道该记录将是什么 - 在没有特定选择或排序标准的情况下,数据库可以自由地以它关心的任何顺序返回行。它可能会返回您插入的最后一行 - 但它可能会返回表中的任何随机行。根据 ROWNUM=1,您根本无法知道您将把最后一行插入到表中。
幸运的是,您不需要执行任何这些操作,因为您已经可以访问刚刚通过:NEW
伪行插入的行。我建议将您的触发器重写为:
create or replace trigger actualizar_stock
after insert on ORDER_ITEMS
for each row
begin
--UPDATE (REST THE CURRENT VALUE WITH THE ORDERED AMOUNT)
update inventories
set quantity_on_hand = quantity_on_hand - :NEW.QUANTITY
where QUANTITY_ON_HAND > 0 AND
product_id = :NEW.PRODUCT_ID;
IF SQL%ROWCOUNT = 0 THEN
-- No rows updated
dbms_output.put_line('Registration not updated');
end if;
end actualizar_stock;
祝你好运。
推荐阅读
- php - 谷歌表格错误
- ios - Segue Right,Segue Left throws:应用程序试图在 Swift 中以模态方式呈现一个活动控制器。为什么?
- docker - 构建后如何从构建中删除中间图像?
- spring - 如何使用 log4j2.xml 中 application.yml 中定义的变量 ${variable}
- c# - 单击父窗口时的WPF模态无边框窗口效果
- java - 春天的注释有什么用?
- javascript - 单击按钮时动态添加/创建选择器
- go - 试图避免 goroutine 泄漏时出现恐慌
- php - 我怎样才能在所有 DIV、RevSlider 等前面发出我的隐私警报
- php - 根据输入字段对html表进行排序