0

当我尝试从我的应用程序运行 SQL 映射时,我得到一个无效的列名。基本上我有两个独立的映射文件,它们基本上做同样的事情,除了创建一个不同名称的列。请注意,我故意留下了 DROP TABLE 来说明这个问题。我知道这是一种不好的做法,但我正在寻找为什么会发生这种情况。此后,我们通过显式删除每个 SQL 映射中的表来纠正此行为。

查询1:

<select id="Query1"   parameterClass="query1Criteria">   

    IF Object_Id('tempdb..##severity') IS NOT NULL     
    BEGIN
      DROP TABLE ##severity
    END     

    CREATE TABLE ##severity( valueCode VARCHAR(255) NOT NULL, displayOrder INT NOT NULL)
    INSERT INTO ##severity
        SELECT DISTINCT valueCode,MAX(displayOrder) FROM DataDictionaryValue
        WHERE zoneID = #zoneID# AND categoryCode = 'SEVERITY'
        GROUP BY valueCode 

    SELECT valueCode FROM ##severity

</select>

查询 2:

<select id="Query2" parameterClass="query2Criteria">   

    IF Object_Id('tempdb..##severity') IS NOT NULL     
    BEGIN
      DROP TABLE ##severity
    END     

    CREATE TABLE ##severity( severityCode VARCHAR(255) NOT NULL, displayOrder INT NOT NULL)
    INSERT INTO ##severity
        SELECT DISTINCT valueCode,MAX(displayOrder) FROM DataDictionaryValue
        WHERE zoneID = #zoneID# AND categoryCode = 'SEVERITY'
        GROUP BY valueCode 

    SELECT severityCode FROM ##severity

</select>

从应用程序中,我运行 Query1。执行得很好,我看到了在 SQL Management Studio 中创建的临时表。然后我执行 Query2,并获得以下堆栈跟踪:

org.springframework.jdbc.BadSqlGrammarException: SqlMapClient operation; bad SQL grammar []; nested exception is com.ibatis.common.jdbc.exception.NestedSQLException:   
--- The error occurred in com/test/model/safety/reports/Query2Map.xml.  
--- The error occurred while applying a parameter map.  
--- Check the Query2.getResults-InlineParameterMap.  
--- Check the statement (query failed).  
--- Cause: java.sql.SQLException: Invalid column name 'severityCode'.
    at org.springframework.jdbc.support.SQLErrorCodeSQLExceptionTranslator.translate(SQLErrorCodeSQLExceptionTranslator.java:276)
    at org.springframework.orm.ibatis.SqlMapClientTemplate.execute(SqlMapClientTemplate.java:212)
    at org.springframework.orm.ibatis.SqlMapClientTemplate.executeWithListResult(SqlMapClientTemplate.java:249)
    at org.springframework.orm.ibatis.SqlMapClientTemplate.queryForList(SqlMapClientTemplate.java:296)
    at com.test.model.BaseSqlMapDao.executeQueryForList(BaseSqlMapDao.java:53)
    at com.test.model.safety.reports.Query2SqlMapDao.getOpenIssues(Query2SqlMapDao.java:124)
    at com.test.model.safety.reports.Query2SqlMapDao.getResults(Query2SqlMapDao.java:50)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)

如果我在 SMS 中运行 Query2 的 SQL,它将正确执行。事实上,这两个查询都将在 SMS 中正确执行。我不了解 iBatis 的详细工作原理,但是 iBatis 似乎看到了在 Query1 中创建的临时表,并针对该模式验证了 Query2 的语法,在这种情况下会抛出无效的列名异常。然而,这意味着 iBatis 保留对临时表的引用,这与 SQL 服务器范式相矛盾,其中临时表的范围仅限于连接。

谁能解释这里发生了什么?

4

2 回答 2

0

也许您可以使用表变量而不是临时表。

它看起来像:

DECLARE @severity as TABLE ( valueCode VARCHAR(255) NOT NULL, displayOrder INT NOT NULL)

INSERT INTO @severity
    SELECT DISTINCT valueCode,MAX(displayOrder) FROM DataDictionaryValue
    WHERE zoneID = #zoneID# AND categoryCode = 'SEVERITY'
    GROUP BY valueCode 

SELECT valueCode FROM @severity

您也可以删除DISTINCT关键字。GROUP BY valueCode已经确保了不同的 valueCode 值。

于 2012-12-13T22:14:03.320 回答
0

由于插入数据的表的列名与从中获取数据的表的列名不匹配,它会引发错误。

 CREATE TABLE ##severity( severityCode VARCHAR(255) NOT NULL, displayOrder INT NOT NULL)
INSERT INTO ##severity
    SELECT DISTINCT valueCode,MAX(displayOrder) FROM DataDictionaryValue
    WHERE zoneID = #zoneID# AND categoryCode = 'SEVERITY'
    GROUP BY valueCode 

SELECT severityCode FROM ##severity    

在前面的代码片段中,您在内部查询中选择 valueCode 并将其插入到没有 valueCode 列名称的 ##severity 临时表中。

于 2018-06-15T09:16:51.540 回答