BizTalk - 使用表变量参数从 Oracle 存储过程生成模式

发布于 2024-10-11 01:29:01 字数 2659 浏览 4 评论 0原文

我正在尝试在 BizTalk 中设置一个简单的示例项目,该项目获取对 SQL Server 数据库中的表所做的更改并更新 Oracle 数据库中该表的副本。

在 SQL Server 端,我有一个名为 GetItemChanges() 的存储过程,它返回可变数量的记录。

在 Oracle 方面,我有一个名为 Update_Item_Region_Table() 的存储过程,旨在将记录表作为参数,以便它可以在一次调用中处理从 GetItemChanges() 返回的所有记录。它的定义如下:

create or replace type itemrec is OBJECT (
        UPC                VARCHAR2(15),
        REGION             VARCHAR2(5),
        LONG_DESCRIPTION   VARCHAR2(50),
        POS_DESCRIPTION    VARCHAR2(30),
        POS_DEPT           VARCHAR2(5),
        ITEM_SIZE          VARCHAR2(10),
        ITEM_UOM           VARCHAR2(5),
        BRAND              VARCHAR2(10),
        ITEM_STATUS        VARCHAR2(5),
        TIME_STAMP         VARCHAR2(20),
        COSTEDBYWEIGHT     INTEGER
);

create or replace type tbl_of_rec is table of itemrec;

create or replace PROCEDURE Update_Item_Region_table  ( Item_Data  tbl_of_rec ) 
IS
 errcode integer; 
 errmsg varchar2(4000); 
BEGIN 
   for recIndex in 1 .. Item_Data.COUNT
   loop

   update FL_ITEM_REGION_TEST set
      Region            = Item_Data(recIndex).Region,
      Long_description  = Item_Data(recIndex).Long_description,
      Pos_Description   = Item_Data(recIndex).Pos_description,
      Pos_Dept          = Item_Data(recIndex).Pos_dept,
      Item_Size         = Item_Data(recIndex).Item_Size,
      Item_Uom          = Item_Data(recIndex).Item_Uom,
      Brand             = Item_Data(recIndex).Brand,
      Item_Status       = Item_Data(recIndex).Item_Status,
      Timestamp         = to_date(Item_Data(recIndex).Time_stamp, 'yyyy-mm-dd HH24:mi:ss'),
      CostedByWeight    = Item_Data(recIndex).CostedByWeight
   where
      UPC = Item_Data(recIndex).UPC;

   log_message(Item_Data(recIndex).Region, '', 'Updated item ' || Item_Data(recIndex).UPC || '.');

   end loop;

 EXCEPTION 
 WHEN OTHERS THEN 
 errcode := SQLCODE(); 
 errmsg := SQLERRM(); 
 log_message('CE', '', 'Error in Update_Item_Region_table(): Code [' || errcode || '], Msg [' || errmsg || ']  ...'); 
END;

在我的 BizTalk 项目中,我为两个存储过程生成架构和绑定信息。对于 Oracle 过程,我为 GenelatedUserTypesAssemblyFilePath 参数指定了一个路径,以生成包含数据类型定义的 DLL。在服务器上的发送端口中,我将该类型 DLL 的路径放入 UserAssembliesLoadPath 参数中。

我创建了一个映射,将 GetItemChanges() 架构转换为 Update_Item_Region_Table() 架构。

当我运行它时,数据被提取并转换得很好,但在尝试将数据传递到 Oracle 过程时导致异常:

*适配器无法传输消息以发送端口“WcfSendPort_OracleDBBinding_HOST_DATA_Procedure_Custom”,URL 为“oracledb://dvotst/”。它将在为此发送端口指定的重试间隔后重新传输。详细信息:“System.InvalidOperationException:'HOST_DATA.TBL_OF_REC'的自定义类型映射未指定或无效。*

因此,它显然没有将有关自定义数据类型 TBL_OF_REC 的信息获取到类型 DLL 中。

有关如何执行此操作的任何提示工作?

I'm trying to set up a simple example project in BizTalk that gets changes made to a table in a SQL Server db and updates a copy of that table in an Oracle db.

On the SQL Server side, I have a stored proc named GetItemChanges() that returns a variable number of records.

On the Oracle side, I have a stored proc named Update_Item_Region_Table() designed to take a table of records as a parameter so that it can process all the records returned from GetItemChanges() in one call. It is defined like this:

create or replace type itemrec is OBJECT (
        UPC                VARCHAR2(15),
        REGION             VARCHAR2(5),
        LONG_DESCRIPTION   VARCHAR2(50),
        POS_DESCRIPTION    VARCHAR2(30),
        POS_DEPT           VARCHAR2(5),
        ITEM_SIZE          VARCHAR2(10),
        ITEM_UOM           VARCHAR2(5),
        BRAND              VARCHAR2(10),
        ITEM_STATUS        VARCHAR2(5),
        TIME_STAMP         VARCHAR2(20),
        COSTEDBYWEIGHT     INTEGER
);

create or replace type tbl_of_rec is table of itemrec;

create or replace PROCEDURE Update_Item_Region_table  ( Item_Data  tbl_of_rec ) 
IS
 errcode integer; 
 errmsg varchar2(4000); 
BEGIN 
   for recIndex in 1 .. Item_Data.COUNT
   loop

   update FL_ITEM_REGION_TEST set
      Region            = Item_Data(recIndex).Region,
      Long_description  = Item_Data(recIndex).Long_description,
      Pos_Description   = Item_Data(recIndex).Pos_description,
      Pos_Dept          = Item_Data(recIndex).Pos_dept,
      Item_Size         = Item_Data(recIndex).Item_Size,
      Item_Uom          = Item_Data(recIndex).Item_Uom,
      Brand             = Item_Data(recIndex).Brand,
      Item_Status       = Item_Data(recIndex).Item_Status,
      Timestamp         = to_date(Item_Data(recIndex).Time_stamp, 'yyyy-mm-dd HH24:mi:ss'),
      CostedByWeight    = Item_Data(recIndex).CostedByWeight
   where
      UPC = Item_Data(recIndex).UPC;

   log_message(Item_Data(recIndex).Region, '', 'Updated item ' || Item_Data(recIndex).UPC || '.');

   end loop;

 EXCEPTION 
 WHEN OTHERS THEN 
 errcode := SQLCODE(); 
 errmsg := SQLERRM(); 
 log_message('CE', '', 'Error in Update_Item_Region_table(): Code [' || errcode || '], Msg [' || errmsg || ']  ...'); 
END;

In my BizTalk project I generate the schemas and binding information for both stored procedures. For the Oracle procedure, I specified a path for the GeneratedUserTypesAssemblyFilePath parameter to generate a DLL to contain the definition of the data types. In the Send Port on the server, I put the path to that Types DLL in the UserAssembliesLoadPath parameter.

I created a map to translate the GetItemChanges() schema to the Update_Item_Region_Table() schema.

When I run it the data is extracted and transformed fine but causes an exception trying to pass the data to the Oracle proc:

*The adapter failed to transmit message going to send port "WcfSendPort_OracleDBBinding_HOST_DATA_Procedure_Custom" with URL "oracledb://dvotst/". It will be retransmitted after the retry interval specified for this Send Port. Details:"System.InvalidOperationException: Custom type mapping for 'HOST_DATA.TBL_OF_REC' is not specified or is invalid.*

So it is apparently not getting the information about the custom data type TBL_OF_REC into the Types DLL.

Any tips on how to make this work?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

北城孤痞 2024-10-18 01:29:01

如果其他人在执行此类任务时遇到问题,我的问题是在生成架构和绑定文件之前没有正确设置所有属性。

GenerateUserTypesAssemblyFilePath <- 我有这个...

GenerateUserTypesAssemblyKeyFilePath <- 我没有这一套...我将其设置为与其余部分相同的强命名密钥文件的项目。

由于我必须在发送端口中提供 DLL 的完整路径,所以我认为它不需要在 GAC 中 - 但它确实如此 - 所以你必须手动添加它,因为部署过程只放置正常的项目 DLL进入 GAC。

我刚刚从 Visual Studio 命令窗口运行此命令:

gacutil /i [path to the generated user types DLL] /f

In case anyone else has trouble with this type of task, my problem was not having all the properties set correctly before generating the schema and binding files.

GeneratedUserTypesAssemblyFilePath <- I had this one …

GeneratedUserTypesAssemblyKeyFilePath <- I did NOT have this one set … I set it to the same strong named key file I used for the rest of the projects.

Since I had to provide the full path to the DLL in the Send Port, I didn’t think it needed to be in the GAC – but it does - so you have to add it manually since the Deploy process only puts the normal project DLLs into the GAC.

I just ran this command from the Visual Studio command window:

gacutil /i [path to the generated user types DLL] /f
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文