Выполнение хранимых процедур с параметрами даты:Командный объект против Объекта Подключения

StackOverflow https://stackoverflow.com/questions/83038

Вопрос

При передаче дат в хранимую процедуру через параметр я немного запутался в том, какой формат использовать для дат.Мой исходный синтаксис VBA использовал объект ADO Connection для выполнения хранимой процедуры:

Set SentDetailRS = Me.ADOConnectionToIntegrity.Execute("dbo.s_SelectAggregatedSentDetailList '" & fCSQLDate(EffectiveDate) & "'", , adCmdText)

Это прекрасно работает для меня, используя синтаксис даты yyyy-mm-dd но когда другой пользователь выполняет код, он получает сообщение об ошибке:13 "Несоответствие типов".

После некоторых экспериментов я обнаружил, что предоставление даты в формате dd/mm/yyyy исправляет эту ошибку для пользователя, но теперь выдает мне ошибку!

Выполнение хранимой процедуры с использованием объекта command с параметрами работает независимо от формата даты (я предполагаю, что ADO заботится о форматировании за кулисами).Я думал, что используя формат yyyy-mm-dd будет ли работать универсально с SQL Server?

Я также озадачен тем, почему эта проблема, по-видимому, зависит от конкретного пользователя?Я заметил, что моим языком по умолчанию на SQL Server является "Английский", тогда как языком по умолчанию для другого пользователя является "Британский английский", может ли это вызвать проблему?

Я использую ADO 2.8 с Access 2003 и SQL Server 2000, вход в систему SQL Server осуществляется через интегрированную систему безопасности Windows.

Это было полезно?

Решение

Будьте осторожны и не верьте, что ADO решает проблему.Универсальным форматом даты SQL является "YYYYMMDD", в то время как региональные настройки компьютера влияют на то, как SQL и ACCESS отображают даты и преобразуют их в символьные строки.

Не забывайте, что разделитель даты - # в Access, в то время как в SQL он равен '

Моим лучшим советом будет систематически преобразовывать ваш код доступа #MM-DD-YYYY# (или аналогичный) в 'ГГГГММДД' перед отправкой инструкции на ваш сервер.Вы могли бы создать небольшую функцию, такую как:

Public function SQLdateFormat(x_date) as string

SQLDateFormat = _
   trim(str(datePart("yyyy",x_date))) & _
   right(str(datePart("m",date)),2) & _
   right(str(datePart("d",date)),2)

   ''be carefull, you might get something like '2008 9 3'
SQLDateFormat = replace(functionSQLDateFormat," ","0")
   '' you will have the expected '20080903'

End function

Если вы не создадите свою строку ВСТАВКИ / ОБНОВЛЕНИЯ программно перед отправкой ее на сервер, я посоветую вам изменить региональные настройки всех компьютеров на региональные настройки машины, на которой размещен SQL.Возможно, вам также придется проверить, существует ли определенный формат даты на вашем SQL server (я не уверен).Лично я решил такого рода проблемы с локализацией (это также случается, когда coma используется как десятичный разделитель во французском языке) или проблемы с конкретными символами SQL (когда в строке используются кавычки или двойные кавычки), удалив инструкции SQL перед отправкой их на сервер.

Другие советы

Я бы предположил, что функция fCSQLDate зависит от конкретной культуры, т. е.он проанализирует дату на основе языковых настроек пользователя.Вот почему вы видите проблему.

В любом случае, использование запросов с объединенными строками всегда является плохой идеей (инъекционные атаки).Вам будет лучше, если вы будете использовать параметры.

Access использует # в качестве разделителя поля даты.Формат должен быть #мм / дд /гггг # вероятно, #мм-дд-гггг # также будет работать нормально.

Извините, я не знаю mysql, но с oracle я бы всегда четко указывал формат, в котором я ожидал, что формат будет, например:"ДД-ММ-ГГГГ", чтобы избежать проблем с (региональным) форматом даты

Почему бы не использовать этот формат

dd mmm yyyy

Есть только один способ, которым это можно истолковать.

Вы можете использовать функцию Date() для возврата универсальной даты на основе настроек даты и времени компьютера.Настройки региона на компьютере будут определять, как он будет отформатирован на стороне клиента.Если вы оставите это поле как строгое поле даты и времени, то настройки региона cleint могут отформатировать дату.

Зайдя на сервер, используйте функцию Date(), которая также должна работать (возвращая универсальное значение даты).

Кроме того, используйте объект command и параметры в вашем запросе при их передаче, чтобы избежать атак SQL-инъекций на строковые поля.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top