VBA 中 ODBCConnection.CommandText 字符串的最大长度是否有解决方法?
Is there a workaround for the maximum length of an ODBCConnection.CommandText string in VBA?
我有一个 VBA 脚本,它为 Excel 中的 SAP HANA ODBC 连接生成查询字符串。查询由用户输入决定,长度可能有很大差异。查询本身使用多个版本的相似查询,并使用 UNION ALL 语法相互附加。
尝试刷新时脚本有时会抛出运行时错误。根据我的研究,很明显这是因为 CommandText 字符串超过了最大允许长度 32,767 (https://ask.sqlservercentral.com/questions/50819/too-long-sql-in-excel-vba.html)。
我想知道除了使用存储过程之外是否有解决此问题的方法(如果有办法 在运行时创建存储过程 那么我不反对执行它,但我不能使用预定义的存储过程,因为我的查询总是不同的,因此需要 VBA 来创建它)
有关 VBA 中的动态查询的更多信息:
列名和参数都是动态创建的,每次都可以不同
该查询使用产品编号列表组为每个产品组生成一个 IN 语句,然后汇总该组名称下这些产品的销售额。然后将这些全部联合起来创建一个 table 和分组记录
用户输入示例:
结果查询示例:
WITH SOME_CTE (SOME_FIELDS) AS
(SELECT SOME_STUFF
FROM SOME_TABLE
WHERE SOME_STUFF_IS_GOING_ON)
SELECT GEND "Gender", 'Attribute 1' "Attribute", SUM(UNITS) "Units", SUM(VAL) "Value", SUM(MARGIN) "Margin"
FROM SOME_CTE
WHERE PRODUCT IN ('12345', '23456', '34567', '45678')
GROUP BY GEND
UNION ALL
SELECT GEND, 'Attribute 2' ATTR_NAME, SUM(UNITS), SUM(VAL), SUM(MARGIN)
FROM SOME_CTE
WHERE PRODUCT IN ('01234', '02345', '03456', '03567')
GROUP BY GEND
ORDER BY "Gender", "Attribute"
...等等。
如您所见,2 个属性组每个包含 4 个产品没有问题,但是当我们达到大约 30 个每个数百个时,它可能太长了。
注意:我试过将查询字符串重复部分中的字段引用缩短为 1 个字符等,这有助于解决问题。
任何帮助将不胜感激。
一种解决方法是发送多个查询。由于您使用的是 union all
,因此您可以每次执行单个 select
语句,即
在(例如)master 数据库中创建 table(不要创建临时 tables!因为它们将在每次查询后被删除) - 但在此之前,请确保您创建新的table,所以删除旧的(如果存在)(在完成后也删除 table)。现在,每个 select
语句都将更改为 insert
语句,这会将记录插入 so-called 临时 table.
这样,您将避免冗长的查询,您只需发送单个 insert .. into.. select
语句。
最后,要获得所有结果,您只需要简单的 select
查询。获得此数据后,您应该删除 table,因为不再需要它。
我有一个 VBA 脚本,它为 Excel 中的 SAP HANA ODBC 连接生成查询字符串。查询由用户输入决定,长度可能有很大差异。查询本身使用多个版本的相似查询,并使用 UNION ALL 语法相互附加。
尝试刷新时脚本有时会抛出运行时错误。根据我的研究,很明显这是因为 CommandText 字符串超过了最大允许长度 32,767 (https://ask.sqlservercentral.com/questions/50819/too-long-sql-in-excel-vba.html)。
我想知道除了使用存储过程之外是否有解决此问题的方法(如果有办法 在运行时创建存储过程 那么我不反对执行它,但我不能使用预定义的存储过程,因为我的查询总是不同的,因此需要 VBA 来创建它)
有关 VBA 中的动态查询的更多信息:
列名和参数都是动态创建的,每次都可以不同
该查询使用产品编号列表组为每个产品组生成一个 IN 语句,然后汇总该组名称下这些产品的销售额。然后将这些全部联合起来创建一个 table 和分组记录
用户输入示例:
结果查询示例:
WITH SOME_CTE (SOME_FIELDS) AS
(SELECT SOME_STUFF
FROM SOME_TABLE
WHERE SOME_STUFF_IS_GOING_ON)
SELECT GEND "Gender", 'Attribute 1' "Attribute", SUM(UNITS) "Units", SUM(VAL) "Value", SUM(MARGIN) "Margin"
FROM SOME_CTE
WHERE PRODUCT IN ('12345', '23456', '34567', '45678')
GROUP BY GEND
UNION ALL
SELECT GEND, 'Attribute 2' ATTR_NAME, SUM(UNITS), SUM(VAL), SUM(MARGIN)
FROM SOME_CTE
WHERE PRODUCT IN ('01234', '02345', '03456', '03567')
GROUP BY GEND
ORDER BY "Gender", "Attribute"
...等等。
如您所见,2 个属性组每个包含 4 个产品没有问题,但是当我们达到大约 30 个每个数百个时,它可能太长了。
注意:我试过将查询字符串重复部分中的字段引用缩短为 1 个字符等,这有助于解决问题。
任何帮助将不胜感激。
一种解决方法是发送多个查询。由于您使用的是 union all
,因此您可以每次执行单个 select
语句,即
在(例如)master 数据库中创建 table(不要创建临时 tables!因为它们将在每次查询后被删除) - 但在此之前,请确保您创建新的table,所以删除旧的(如果存在)(在完成后也删除 table)。现在,每个 select
语句都将更改为 insert
语句,这会将记录插入 so-called 临时 table.
这样,您将避免冗长的查询,您只需发送单个 insert .. into.. select
语句。
最后,要获得所有结果,您只需要简单的 select
查询。获得此数据后,您应该删除 table,因为不再需要它。