Skip to Content

原文链接:https://www.experiencesaphana.com/community/blogs/blog/2012/04/17/developer-s-journal-abaphana-connectivity-via-secondary-database-connection

介绍

在HANA开发日志中,我对开发人员进入HANA世界的方法只是蜻蜓点水了一下。今天,我想描述下我过去几天研究了很久的场景:即在目前的环境下,从ABAP访问HANA。对于这一点,我想说的是目前可以建立的东西。我们都知道,SAP对于在HANA上运行ABAP特定功能已经有令人兴奋的计划,但是,每个人可能不知道的是当HANA作为ABAP系统的辅助数据库时,现在有什么可以做到的?这正是SAP如何构建现在的HANA加速器(方法),所以,花点时间来学习这些是如何建立以及ABAP环境中哪些开发选项支持该场景是很值得的。

HANA作为辅助数据库

我现在描述的场景在HANA的实施中是很常见的:你把HANA安装为辅助数据库,而不是替换了当前数据库。
然后你使用复制(replication)把数据的拷贝移至HANA系统中。你的ABAP程序得到加速,通过读取HANA而非本地数据库的数据。纵观本博客的其余部分,我想讨论如何执行加速读取的技术方案。

/wp-content/uploads/2012/08/11_131378.jpg

前提条件:

  • SAP HANA客户端安装到了每个ABAP应用服务器,并且其操作系统必须支持HANA客户端(检查平台可用性矩阵(Platform Availability Matrix)支持的操作系统 )。
  • SAP HANA DBSL 已安装(这是数据库特定的库,是ABAP内核的一部分)
  • SAP HANA DBSL只在ABAP Kernel 7.20中可用
    ◦Kernel 7.20已经是NetWeaver 7.02, 7.03, 7.20, 7.30 and 7.31的内核
    ◦Kernel 7.20向下兼容,同时也适用NetWeaver 7.00, 7.01, 7.10, and 7.11
  • 你的ABAP系统必须是Unicode

接下来,你的ABAP系统必须进行配置来连接到这个替代数据库。你有一个保存数据库连接字符串,用户名和密码的集中地方。然后你的应用只要指定使得数据库连接信息应用独立的配置键。
该配置可以通过对于表DBCON的表维护(SM30)实现。在配置屏幕上,您要提供DBMS类型(HANA为HDB),你要使用的所有连接和连接字符串的用户名和密码。务必包括HANA的系统端口号,应该是3<实例号>15,所以如果你的HANA的实例号为01,端口号就为30115。

/wp-content/uploads/2012/08/12_131379.jpg

DBCON也可以通过代码DBACOCKPIT来维护,最后你会得到和DBCON一样的记录,但是你会看到更多的信息(例如默认的模式等),然后你可以从那里测试连接。

/wp-content/uploads/2012/08/13_131380.jpg

通过Open SQL连接辅助数据库

从ABAP端执行辅助数据库的SQL操作最简单的方法是,使用ABAP开发人员已经熟悉的Open SQL语句。如果您提供CONNECTION额外的语法(dbcon),你可以强制在替代数据库执行Open SQL语句。

例如,我们拿一个简单的SELECT语句,然后在HANA上执行:

 

  1.   SELECT * FROM sflight CONNECTION (‘AB1’)  
  2.     INTO TABLE lt_sflight  
  3.    WHERE carrid = ‘LH’.

这种方法的好处就是它的简单性。利用已存在的SQL语句一个小小的附加参数,你可以把你的操作重定向到HANA 中。缺点是你正在访问的表或视图必须存在于ABAP数据字典中。这对于加速器场景来说不是一个大问题,考虑到所有的数据都驻留在ABAP DBMS中并复制到HANA。这种情况下,我们总是在ABAP数据字典中有表的本地拷贝。这意味着,你不能访问特定的HANA程序,例如分析视图或是数据库存储过程。你也不能访问任何使用HANA作为主要持久层的表。

通过本地SQL连接辅助数据库

ABAP同样也有使用本地SQL的能力。这种情况下,你要写数据库相关的SQL语句。这使得你可以访问底层数据库中的表和其他工件(artifact)。本地SQL也有调用数据库过程的语法。如果我们拿上面的例子,可以用本地SQL来重写:

 

  1. EXEC SQL.  
  2.     connect to ‘AB1’ as ‘AB1’  
  3.   ENDEXEC.  
  4.   EXEC SQL.  
  5.     open dbcur for select * from sflight where mandt = :sy-mandt and carrid = ‘LH’  
  6.   ENDEXEC.  
  7.   DO.  
  8.     EXEC SQL.  
  9.       fetch next dbcur into :ls_sflight  
  10.     ENDEXEC.  
  11.     IF sy-subrc NE 0.  
  12.       EXIT.  
  13.     ELSE.  
  14.       APPEND ls_sflight TO lt_sflight.  
  15.     ENDIF.  
  16.   ENDDO.  
  17.   EXEC SQL.  
  18.     close dbcur  
  19.   ENDEXEC.  
  20.   EXEC SQL.  
  21.     disconnect ‘AB1’  
  22.   ENDEXEC. 

这里代码当然比Open SQL多,也没有那么优雅,因为我们使用数据库的游标取得数据矩阵。但是好处是可以访问到否则没有的特点。例如,我可以把数据插入到HANA表中,然后使用HANA数据库序列号作为数的范围或是数据库内置的函数类似now()。

 

  1.     EXEC SQL.  
  2.       insert into “REALREAL”.”realreal.db/ORDER_HEADER”  
  3.        values(“REALREAL”.”realreal.db/ORDER_SEQ”.NEXTVAL,  
  4.                    :lv_date,:lv_buyer,:lv_processor,:lv_amount,now() )  
  5.     ENDEXEC.  
  6.     EXEC SQL.  
  7.       insert into “REALREAL”.”realreal.db/ORDER_ITEM” values((select max(ORDER_KEY)  
  8.         from “REALREAL”.”realreal.db/ORDER_HEADER”),0,:lv_product,:lv_quantity,:lv_amount)  
  9.     ENDEXEC. 

另一个通过EXEC SQL使用本地SQL的坏处是,对于你建立的SQL语句没有任何语法检查。错误直到运行时才会捕捉,如果异常没有正确的处理会导致短时当机,这也使得测试很有必要。

通过本地SQL-ADBC 连接辅助数据库

第三个选择提供了通过EXEC SQL连接本地SQL的好处,也在某些限制上做了改进。这是ADBC-ABAP数据连接的概念。基本上,它是一系列类(CL_SQL*)简化和抽象了EXEC SQL区块。例如,我们再次重写我们的SELECT * FROM SFLIGHT example例子:

 

 

  1. ****Create the SQL Connection and pass in the DBCON ID to state which Database Connection will be used  
  2.   DATA lr_sql TYPE REF TO cl_sql_statement.  
  3.   CREATE OBJECT lr_sql  
  4.     EXPORTING  
  5.       con_ref = cl_sql_connection=>get_connection( ‘AB1’ ).  
  6. ****Execute a query, passing in the query string and receiving a result set object  
  7.   DATA lr_result TYPE REF TO cl_sql_result_set.  
  8.   lr_result = lr_sql->execute_query(  
  9.     |SELECT * FROM SFLIGHT WHERE MANDT = { sy-mandt } AND CARRID = ‘LH’| ).  
  10. ****All data (parameters in, results sets back) is done via data references  
  11.   DATA lr_sflight TYPE REF TO data.  
  12.   GET REFERENCE OF lt_sflight INTO lr_sflight.  
  13. ****Get the result data set back into our ABAP internal table  
  14.   lr_result->set_param_table( lr_sflight ).  
  15.   lr_result->next_package( ).  
  16.   lr_result->close( ). 

这里,我们至少去除了数据库游标的分步处理,取而代之的是把数据的整个包一次性读取到内表中。默认情况下,初始包的大小会返回所有结果记录的条数,但是你可以指定任何你想要的包大小,从而调整对大返回结果集的处理。对HANA场景中最重要的是ADBC使你可以访问非数据字典的工件,包括HANA存储过程。鉴于ADBC对于EXEC SQL的优势,SAP推荐总是尝试使用基于ADBC类的接口。

结束语

这还真的只是开始,你可以用这个加速器方法把ABAP集成到SAP HANA中。我在我例子中使用了最简单的SQL语句,以求更集中于技术整合是如何工作的细节。不过,当你执行更有力的语句(SELECT SUM … GROUP BY)、访问HANA特定的工件(如在OLTP表上的OLAP视图)或是存储过程,真正的威力才会显现。这些都是我将在未来我的博客中讨论的主题。

To report this post you need to login first.

1 Comment

You must be Logged on to comment or reply to a post.

Leave a Reply