摘要:[.NET] Oracle Client Exception - ORA-01722
最近的專案使用Oracle DB。在.NET裡可以使用Oracle Client,來對Oracle DB下SQL指令。寫了下面的程式碼,用來取得User資料表裡的User資料。
using (OracleConnection connection = new OracleConnection(connectionString))
{
connection.Open();
using (OracleCommand command = new OracleCommand())
{
command.Connection = connection;
command.Parameters.Add(":lastName", "Chou");
command.Parameters.Add(":firstName", "Clark");
command.CommandText = @"SELECT * FROM USER_DATA WHERE FIRST_NAME=:firstName AND LAST_NAME=:lastName";
using (OracleDataReader reader = command.ExecuteReader())
{
while (reader.Read())
{
// XXXXXXX
}
connection.Close();
}
}
}
快速打完、按下執行。卻產生了讓人摸不清頭緒的錯誤例外「ORA-01722:無效的數字」。
搞了半天才發現使用OracleCommand.Parameters來加參數是有順序性的。在OracleCommand.CommandText裡參數出現的順序,必須要和OracleCommand.Parameters是一致的。也就是下列的程式碼才能正常執行:
using (OracleConnection connection = new OracleConnection(connectionString))
{
connection.Open();
using (OracleCommand command = new OracleCommand())
{
command.Connection = connection;
command.Parameters.Add(":firstName", "Clark");
command.Parameters.Add(":lastName", "Chou");
command.CommandText = @"SELECT * FROM USER_DATA WHERE FIRST_NAME=:firstName AND LAST_NAME=:lastName";
using (OracleDataReader reader = command.ExecuteReader())
{
while (reader.Read())
{
// XXXXXXX
}
connection.Close();
}
}
}
在網路上與朋友討論這個問題與解法。經由Demo的提點,才知道原來只要將OracleCommand.BindByName設定為True就可以解決這個問題。範例程式如下:
using (OracleConnection connection = new OracleConnection(connectionString))
{
connection.Open();
using (OracleCommand command = new OracleCommand())
{
command.BindByName = true;
command.Connection = connection;
command.Parameters.Add(":lastName", "Chou");
command.Parameters.Add(":firstName", "Clark");
command.CommandText = @"SELECT * FROM USER_DATA WHERE FIRST_NAME=:firstName AND LAST_NAME=:lastName";
using (OracleDataReader reader = command.ExecuteReader())
{
while (reader.Read())
{
// XXXXXXX
}
connection.Close();
}
}
}
趁還有印象快速紀錄一篇下來,為自己做個紀錄,也希望能幫助到有需要的開發人員。 當然也要再次感謝Demo大大。:D
能以更簡潔的文字與程式碼,傳達出程式設計背後的精神。
真正做到「以形寫神」的境界。