2012-05-22 33 views
2

我在使用Nhbernate中的位置參數時遇到問題。「?」附近的語法錯誤:Nhibernate生成的查詢

條件GroupProperty使用命名變量和位置變量發送sql。

本聲明:

session.CreateCriteria(typeof(MatchStageFrom)) 
       .SetProjection(Projections.GroupProperty(
        Projections.SqlFunction("substring", NHibernateUtil.String, Projections.Property("LastName"), Projections.Constant(0), Projections.Constant(1)) 
        ) 
       ); 

是生產這個SQL:

SELECT substring(this_.LAST_NAME, @p0, @p1) as y0_ FROM MATCH_STAGING_FROM this_ GROUP BY substring(this_.LAST_NAME, ?, ?) 

導致SQL與錯誤:

Incorrect syntax near '?'. 

could not execute query 
[ SELECT substring(this_.LAST_NAME, @p0, @p1) as y0_ FROM MATCH_STAGING_FROM this_ GROUP BY substring(this_.LAST_NAME, ?, ?) ] 
Positional parameters: #0>0 #1>1 #2>0 #3>1 
[SQL: SELECT substring(this_.LAST_NAME, @p0, @p1) as y0_ FROM MATCH_STAGING_FROM this_ GROUP BY substring(this_.LAST_NAME, ?, ?)] 

我能做些什麼來解決這個問題?

+1

很高興知道我不是唯一一個誰經歷過這個。 –

回答

0

它看起來像NHibernate的一個bug,但如果你只是想那些結果您可以通過使用Projections.Distinct代替Projections.GroupProperty,即得到同樣的結果:

session.CreateCriteria(typeof(MatchStageFrom)) 
      .SetProjection(Projections.Distinct(
       Projections.SqlFunction("substring", NHibernateUtil.String, 
        Projections.Property("LastName"), 
        Projections.Constant(0), 
        Projections.Constant(1)) 
       ) 
      ); 

另外,如果你是選擇的不僅僅是名字的第一個字符,那麼你可能可以讓它使用子查詢

0

我碰到類似的問題Projections.SqlFunction("concat" ...)。最後,我用Projections.SqlProjection(...)來解決這個問題。我不喜歡這個答案,因爲我認爲它可能不太方便,但它確實對我有用。

0

解決方法

使用組由和SqlFunction參數當在NHibernate的一個錯誤。 「如果一個應用Projections.GroupProperty(customProjection),在投影參數只發送一次(對SELECT條款),而GROUP BY子句中的參數位置,並在查詢失蹤......」 (see

然同樣的漏洞,並解決它在運行時添加自定義SQL函數NHibernate的, (see

解決方法移動常數參數走出Projections.SqlFunction呼叫,進入自定義函數的定義(「year_week」) 。

老失敗:

Projections.GroupProperty(
    Projections.Cast(NHibernateUtil.AnsiString, 
     Projections.SqlFunction("to_char", NHibernateUtil.AnsiChar, 
     Projections.Property(() => myAlias.Date), 
     Projections.Constant("IYYYIW") // Turns into "?" in group by 
    ) 
    ) 
) 

解決方法:

Projections.GroupProperty(
    Projections.Cast(NHibernateUtil.AnsiString, 
     Projections.SqlFunction("year_week", NHibernateUtil.AnsiChar, 
     Projections.Property(() => myAlias.Date) 
     // constant moved to function definition 
    ) 
    ) 
) 

功能 「year_week」 定義如下:

DialectExtensions.RegisterFunction(sessionFactory, "year_week", new SQLFunctionTemplate(NHibernateUtil.String, "TO_CHAR(?1,'IYYYIW')"));