如何从插件SQL源代码中的Region Source SQL Select语句获取结果表?

VEL*_*LFR 5 plsql oracle-apex oracle-apex-5.1

我目前正在为Region开发APEX插件.它执行一些JavaScript代码,SELECT结果转换为字符串.但出于测试原因,SELECT查询暂时写入插件的源PL/SQL代码.

源代码看起来像这样:

FUNCTION f_render (p_region in apex_plugin.t_region, p_plugin in apex_plugin.t_plugin)
RETURN apex_plugin.t_region_render_result IS 
  v_js VARCHAR(512);
  v_data VARCHAR(1024);
BEGIN
  SELECT '[' || c_matrix || ']' INTO v_data FROM (
    SELECT listagg(c_row, ',') WITHIN GROUP (ORDER BY c_row) AS c_matrix FROM (
      -- next line should be re-written 
      -- for compatibility with any possible origin or target string 
      -- values and numbers, but it's another question
      SELECT '[' || "'a'" || ',' || "'b'" || ']' AS c_row FROM ( 
        -- actual test table query that should be in p_region.source
        WITH t0 AS ( 
          SELECT 'a' origin, 'a' target, 11 amount FROM dual UNION ALL
          SELECT 'a', 'b', 21 FROM dual UNION ALL
          SELECT 'b', 'a', 12 FROM dual UNION ALL
          SELECT 'b', 'b', 22 FROM dual
        ), t1 AS (
          SELECT * FROM t0
          PIVOT ( sum(amount) for target in ('a','b'))
          ORDER BY origin
        )
        SELECT * FROM t1
      )
    )
  ); 
  v_js := q'[
    console.log("@DATASTRING@");
  ]';
  v_js := REPLACE(v_js, '@DATASTRING@', v_data);
  apex_javascript.add_onload_code(p_code => v_js, p_key => null);
  RETURN NULL;
END f_render; 
Run Code Online (Sandbox Code Playgroud)

"实际测试表" SELECT返回此t1表:

|ORIGIN|'a'|'b'|
|------|---|---|
| a    | 11| 21|
| b    | 12| 22|
Run Code Online (Sandbox Code Playgroud)

console.log打印一个这样的字符串:[[11,21],[12,22]].而且,如果我调整一些东西,这个插件甚至会在浏览器控制台中返回这个JS数组,就像它应该的JS数组一样.

这些是现在所需和正确的结果.但是,如果我改变"实际测试表" SELECTp_region.source,并把这个SELECTSource: SQL QueryPage Designer,它不会在所有的工作,并且APEX不希望这个插件保存由于一些错误.

p_region.source应该能够使用任何SELECT,甚至是简单的东西SELECT * FROM table_A,在哪里table_A是类似于"实际测试表"的旋转矩阵t1.

问题:如何正确引用查询结果p_region.source以使其全部工作?AFAIK,它可以用APEX_PLUGIN_UTIL.GET_DATA或完成.GET_DATA2.但我不知道它返回什么以及测试它的方式和位置.我想用像dbfiddle这样的东西来玩它来学习它的作用.

PS:我是大三学生,但无论我的资格如何,我的老板都给了我这个任务.在这种情况下,Oracle Documentation也不是很有帮助.

Dmi*_*riy 5

首先,什么会帮助你发展一般。在开发 Region Plug-in 时,有两种方式可以查看调试信息:通常的数据记录到表格中或直接在页面上输出。对于第一种方式(登录到表中),您需要创建一个表(具有您需要的任何结构)并从您的 PL/SQL 代码中插入行。第二种方式使用htp.p程序直接在网页中输出数据。例如,如果将以下代码放入渲染插件函数中:

select some_value
  into v_variable
  from table1
 where ... ;

htp.p('Variable contains: ' || v_variable || '<br />');
Run Code Online (Sandbox Code Playgroud)

此代码将创建如下内容:

<div> <!-- open and close div tags are generated by APEX engine -->
  Variable contains: 123<br />
</div>
Run Code Online (Sandbox Code Playgroud)

您需要创建一个页面,在其上创建一个带有您的插件类型的区域,然后在浏览器中打开该页面。之后,您将看到输出。

接下来,如何处理SQL查询。APEX_PLUGIN_UTIL.GET_DATA返回一个 type 的值apex_plugin_util.t_column_value_list,它只是一个字符串集合的集合。你必须使用这个函数的主要原因是它也可以绑定SQL代码中的任何绑定变量。例如,如果您有一个页面项P1_VALUE并希望在查询中使用其值,则可以放入区域的源:

select *
  from table
 where column1 = :P1_VALUE
Run Code Online (Sandbox Code Playgroud)

APEX_PLUGIN_UTIL.GET_DATA 将在这里自动绑定一个项目的值。

如何处理结果。以下代码将输出一个简单的 html 表:

  ...
  v_data apex_plugin_util.t_column_value_list;
begin
  ...
  v_data := apex_plugin_util.get_data(p_region.source, 1, 10, p_region.name);

  htp.p('<table><tbody>');

  for i in v_data.first .. v_data.last loop
    htp.p('<tr>');

    for j in v_data(i).first .. v_data(i).last loop
      -- your code to process data
      htp.p('<td>' || v_data(i)(j) || '</td>');
    end loop;

    htp.p('</tr>');
  end loop;
  htp.p('</tbody></table>');
  ...
end;
Run Code Online (Sandbox Code Playgroud)

请注意,此函数返回(出于某种原因)转置表。因此,如果您有一个包含两列三行的表格:

COL1  COL2
----------
abc    123
def    456
ghi    789
Run Code Online (Sandbox Code Playgroud)

上面代码的输出将是:

<table>
  <tbody>
    <tr>
      <td>abc</td><td>def</td><td>ghi</td>
    </tr>  
    <tr>
      <td>123</td><td>456</td><td>789</td>
    </tr>
  </tbody>
</table>
Run Code Online (Sandbox Code Playgroud)