Мы создаем клиентскую программу, в которой параметры для хранения на веб-сервере с серверной частью Oracle задаются в клиентской программе .Net и загружаются в виде набора данных через веб-сервис.
В коде веб-службы данные считываются из набора данных и добавляются в операторы UPDATE на веб-сервере (серверная часть Oracle).
Поскольку сервер будет работать в локальной сети заказчика за брандмауэром и из-за динамической природы используемых параметров, sprocs не используются - строки SQL встроены в логику.
Вот пример строки:
UPDATE WorkOrders
SET TravelTimeHours = :TravelTimeHours,
TravelTimeMinutes = :TravelTimeMinutes,
WorkTimeHours = :WorkTimeHours,
WorkTimeMinutes = :WorkTimeMinutes,
CompletedPersonID = :CompletedPersonID,
CompletedPersonName = :CompletedPersonName,
CompleteDate = :CompleteDate
WHERE WorkOrderNumber = :WorkOrderNumber
При отладке кода в VS 2010 и входе в код сервера мы получаем следующую ошибку:
ORA-01036: illegal variable name/number
при выполнении команды SQL на компьютере-оракуле-получателе нам было предложено ввести привязку
переменные для вышеприведенного оператора, и если мы использовали правильный формат даты, оператор UPDATE
работал правильно.
Вопросы:
1) возможно, что оракул выдал ошибку ORA-01036, когда формат месяца был неправильным?
2) почему бы нам не преобразовать формат даты с веб-сайта ASP.net, работающего на компьютере Oracle?
Oracle имеет стандартную процедуру преобразования, которая исключает экран ввода переменных связывания?
3) если формат даты не был проблемой, что именно означает ORA-1036 и как я могу обнаружить
У какой переменной было недопустимое имя / номер?
Это фрагмент функции, которая принимает тип набора данных (WOName) и возвращает соответствующую строку SQL.
Многие случаи существуют, но были удалены для удобства чтения.
Private Function GetMainSQLString(ByVal WOName As String) As String
Dim Result As String = ""
Select Case WOName
Case "Monthly Site Inspection"
Dim sb As New StringBuilder
sb.Append("UPDATE WorkOrders SET ")
sb.Append("CompletedPersonID = :CompletedPersonID, CompletedPersonName = :CompletedPersonName, CompleteDate = :CompleteDate, ")
sb.Append("SupervisorID = :SupervisorID, SupervisorName = :SupervisorName ")
sb.Append("WHERE WorkOrderNumber = :WorkOrderNumber")
Result = sb.ToString
End Select
Return Result
End Function
Это фрагмент функции, которая принимает объект команды Oracle byRef и добавляет к нему необходимые параметры,
в зависимости от того, какой из 15 возможных типов данных (WOName) получен из клиентской программы.
Многие случаи существуют, но были удалены для удобства чтения.
Обновленный объект Cmd затем возвращается в основную логику программы, где вызывается ExecuteNonQuery ().
Тестовые значения параметров ниже:
dr.Item("CompletedPersonID") 21
dr.Item("CompletedPersonName") Pers Name
dr.Item("CompleteDate") #8/16/2010#
dr.Item("SupervisorID") 24
dr.Item("SupervisorName") Sup Name
dr.Item("WorkOrderNumber") 100816101830
Private Function addMainCmdParams(ByVal WOName As String, ByRef cmd As OracleCommand, ByVal dr As DataRow) As OracleCommand
Select Case WOName
Case "Monthly Site Inspection"
cmd.Parameters.Add(":CompletedPersonID", Oracle.DataAccess.Client.OracleDbType.Int32).Value = dr.Item("CompletedPersonID")
cmd.Parameters.Add(":CompletedPersonName", Oracle.DataAccess.Client.OracleDbType.Varchar2).Value = dr.Item("CompletedPersonName")
cmd.Parameters.Add(":CompleteDate", Oracle.DataAccess.Client.OracleDbType.Date).Value = dr.Item("CompleteDate")
cmd.Parameters.Add(":SupervisorID", Oracle.DataAccess.Client.OracleDbType.Int32).Value = dr.Item("SupervisorID")
cmd.Parameters.Add(":SupervisorName", Oracle.DataAccess.Client.OracleDbType.Varchar2).Value = dr.Item("SupervisorName")
cmd.Parameters.Add(":WorkOrderNumber", Oracle.DataAccess.Client.OracleDbType.Varchar2).Value = dr.Item("WorkOrderNumber")
End Select
Return cmd
End Function
При выполнении этого сегодня этот точный код БЫЛ успешен; но другого подобного случая не было. Я все еще не доверяю любой неявной типизации, выполняемой Oracle (если таковая имеется) - и я особенно подозрительно отношусь к тому, как Oracle обрабатывает любые из этих параметров, которые передаются с помощью dbNull.value - и я знаю, что это произойдет. так что если это проблема, мне придется обойти ее. Слишком много необязательных параметров и столбцов, которые не всегда передают значения для этой системы, чтобы разбить на нули.