調用PostgreSQL存儲過程,找不到函數名的問題


PostgreSQL的表,函數名稱都是嚴格區分大小寫的,所以在使用的時候沒有注意大小寫問題容易導致找不到函數名的錯誤,但最近兩天我們發現,如果函數參數使用了自定義的數據類型,也會發生這個問題。
問題描述:
 
下面的示例測試代碼:

 

 

復制代碼
PWMIS.DataProvider.Data.AdoHelper db = MyDB.GetDBHelperByConnectionName("PostgreSQL");
            IDataParameter para = db.GetParameter();
            para.ParameterName = "@jjdm";
            para.DbType = DbType.AnsiString  ; 
            para.Value = "KF0355";
            int count= db.ExecuteNonQuery("updatefundattention",
                System.Data.CommandType.StoredProcedure,
                new System.Data.IDataParameter[] { para });
復制代碼

 

運行該存儲過程,出現下面的錯誤:
DataBase ErrorMessage:ERROR: 42883function updatefundattention(text) does not exist
SQL:updatefundattention
CommandType:StoredProcedure
Parameters:
Parameter["@jjdm"]    =    "KF0355"              //DbType=String
 
 
實際上,PostgreSQL的函數updatefundattention 參數類型不是 text,而是自定義的類型 citex ,下面是函數定義:

 

復制代碼
CREATE OR REPLACE FUNCTION updatefundattention(jjdm citext)
  RETURNS void AS
$BODY$
DECLARE
  
BEGIN
  update JJZB set gzd=COALESCE(gzd,0)+1 where JJZB.Jjdm=$1 ;
  --return 1;
END;
$BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION updatefundattention(citext) OWNER TO postgres;
復制代碼

 

昨天分析可能PostgreSQL的字符型參數不能使用AnsiString參數類型,需要使用String類型,但今天測試發現
para.DbType = DbType.String  ; 
 
問題依然沒有解決。
重新建立一個測試函數updatefundattention,只是參數類型為 varchar:

 

復制代碼
CREATE OR REPLACE FUNCTION updatefundattention2(jjdm character varying)
  RETURNS void AS
$BODY$
DECLARE
  
BEGIN
  update JJZB set gzd=COALESCE(gzd,0)+1 where JJZB.Jjdm=$1 ;
  --return 1;
END;
$BODY$
  LANGUAGE plpgsql VOLATILE
  COST 100;
ALTER FUNCTION updatefundattention2(character varying) OWNER TO postgres;
復制代碼

 

 

運行測試程序,不論
para.DbType = DbType.AnsiString  ; 
還是
para.DbType = DbType.String  ; 
 
調用函數updatefundattention2 均能通過,故此得到結論:
目前自定義的 citext 類型.NET程序無法設置正確的DbType,從而會出現找不到函數的錯誤!
 
問題影響:
 
在WFT中,所有使用.NET程序調用PostgreSQL存儲過程的代碼,如果存儲過程的參數使用了自定義的類型(例如citex),均會受影響。
 
解決方案:
 
a,建議 不要在PostgreSQL函數的參數中使用自定義的類型,如果要想對參數進行大小寫轉換,建議在函數體中使用另外一個Pgsql變量,函數中執行查詢的SQL語句使用這個新變量,而不是直接使用這個函數參數;
b,修改Sql-Map中的SQL語句,例如
復制代碼
<Select CommandName="AddGuanZhuDu" Method="" CommandType="StoredProcedure" Description="增加關注度" ResultClass="ValueType"><![CDATA[
      UpdateFundAttention
      #jjdm : String#
      ]]></Select>
修改成下面的方式:
<Select CommandName="AddGuanZhuDu" Method="" CommandType="Text" Description="增加關注度" ResultClass="ValueType"><![CDATA[
      select * from UpdateFundAttention (#jjdm: String#)
      ]]></Select>
復制代碼
但這種修改方式會造成SqlServer與PostgreSQL的 SQL-MAP語句不相同,增加程序的維護量,理想的方式是SQL-MAP語句盡量相同。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM