问题
我有一个 SQLRPGLE 程序,它执行如下所示的查询:
SELECT orapdt, oraptm, orodr#, c.ccctls, orbill, b.cuslmn, b.cusvrp, orocty, orost, o.cubzip, o.cucnty, ordcty, ordst, d.cubzip, d.cucnty
FROM order
LEFT JOIN cmtctlf c ON orbill = c.cccode
LEFT JOIN custmast b ON orbill = b.cucode
LEFT JOIN custmast o ON orldat = o.cucode
LEFT JOIN custmast d ON orcons = d.cucode
WHERE
orstat != 'C' AND
orbill IN ('ABCDE', 'VWXYZ', 'JKFRTE') AND
orapdt BETWEEN 2012365 AND 2013362 AND
o.cucnty = 'USA' AND
(o.cubzip LIKE '760%' OR o.cubzip LIKE '761%' OR o.cubzip LIKE '762%') AND
d.cubzip = '38652' AND
ordcty = 'NA' AND
ordst = 'MS' AND
d.cucnty = 'USA'
ORDER BY orapdt, oraptm, orodr#
字段定义:
orapdt 7 0
oraptm 4a
orodr# 7a
c.ccctls 6a
orbill 6a
b.cuslmn 2a
b.cusvrp 3a
orocty 4a
orost 2a
o.cubzip 5a
o.cucnty 3a
ordcty 4a
ordst 2a
d.cubzip 5a
d.cucnty 3a
c.cccode 6a
b.cucode 6a
o.cucode 6a
d.cucode 6a
我在作业日志中看到以下错误:
Field HVR0001 and value 1 not compatible. Reason 7.
Conversion error on host variable or parameter *N.
当我提示输入其他消息信息时,我被告知:
The attributes of variable field HVR0001 in query record format FORMAT0001 are not compatible with the attributes of value number 1. The value is *N. The reason code is 7.
7 -- Value contains numeric data that is not valid
和
Host variable or parameter *N or entry 1 in a descriptor area contains a value that cannot be converted to the attributes required by the statement. Error type 6 occurred.
6 -- Numeric data that is not valid.
这些错误是通过打开游标触发的:
...
exec sql PREPARE S1 FROM :sql_stmt;
exec sql DECLARE C1 SCROLL CURSOR FOR S1;
exec sql OPEN C1;
...
我的 outq 中也有 QSQSVCDMP 文件,其中包含转储信息。我在那里看到的唯一有用的东西是对 CPF4278 和 CPD4374 的引用
CPF4278 表示
Query definition template &1 not valid.
CPD4374 表示
Field &1 and value &3 not compatible. Reason &5.
不幸的是,错误消息本身并不存在,只有字符串“CPF4278”和“CPD4374”。
在我监控 SQL 错误代码的程序中,它们都是相同的:
SQLSTATE: 22023
SQLCODE: -302
SQLERRMC: <non-displayable character>*N
错误状态/代码表示 "A parameter or variable value is invalid."
我试过的...
经过多次谷歌搜索,我尝试过:
当有 ORDER BY 子句时排序)
在右侧的结果记录中)
我想问的是...
如何找出哪个字段中有错误数据?我知道
HVR0001
无效,但哪个字段由 HVR0001
表示?我尝试以不同的顺序选择字段,但总是 HVR0001
具有无效值。理想情况下,我希望能够打印出所有 HVR* 字段/值,以便我可以检查它们。
当我查看编译列表时,没有列出 HVR* 字段。列出了一些 SQL_* 字段,我可以看到
SQL_00011
用于临时保存放入 orapdt
的数据。 SQL_00011
的定义与 orapdt
完全一样(7,0 打包)。这是我查询中唯一的数字字段...我觉得我的问题是由文件的连接方式引起的,不知何故将无效值(可能为 NULL)放入我的
orapdt
字段中。我还认为我的问题与一个接一个地执行许多这些查询有关(每个查询的某些 WHERE 细节会发生变化),因为我可以将失败的查询之一放入它自己的程序中并运行它它工作正常。
这是在 DB2 for i (V6R1) 上,所有涉及的文件都是使用 DDS 创建的
编辑:
这是 LIKE 语句所需的主变量(数据结构)和两个外部数据结构:
d eds_custmast e ds extname('CUSTMAST') inz
d eds_order e ds extname('ORDER') inz
d o ds
d orapdt like(ORAPDT)
d oraptm like(ORAPTM)
d orodr# like(ORODR#)
d orctls like(CUCODE)
d orbill like(ORBILL)
d orslmn like(CUSLMN)
d orcsr like(CUSVRP)
d orocty like(OROCTY)
d orost like(OROST)
d orozip like(CUBZIP)
d orocntry like(CUCNTY)
d ordcty like(ORDCTY)
d ordst like(ORDST)
d ordzip like(CUBZIP)
d ordcntry like(CUCNTY)
// Define an array to indicate nulls...
d o1nv s 3i 0 dim(15)
这是实际获取数据的 fetch 语句:
dow sqlcode = *zeros;
exec sql FETCH NEXT FROM C1 INTO :o :o1nv;
if sqlcode = *zeros;
// process the data.
endif;
enddo;
exec sql CLOSE C1;
我之前没有包含这个只是因为当我打开游标而不是获取一行时会发生错误。 OPEN 语句不应该知道关于
o
数据结构的任何信息。至于 WHERE 子句中的哪些更改 - 所有这些都是动态构建的(因此可以更改),除了:
orstat != 'C' AND orapdt BETWEEN 2012365 AND 2013362
最佳答案
找出实际错误是什么并不容易。我倾向于将这些语句复制到 IBM i Navigator 中,并使用 Visual Explain 来尝试了解优化器正在做出的决策。另一种方法是执行 STRDBG 并查看作业日志。当STRDBG 生效时,优化器将信息性消息放入作业日志中。但即便如此,也很难解开谜团。
在这种情况下,只有一个数字列 orapdt
。尝试没有该列的查询,看看这是否是罪魁祸首。
关于db2 - SQLRPGLE 中 OPEN 游标上的 SQL -302,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/16571234/