|
Проблема связки Delphi: TFireDAC+MSSQL+TVP+datetime2(0) | ☑ | ||
---|---|---|---|---|
0
H A D G E H O G s
06.03.23
✎
22:04
|
День добрый.
Понадобился мне вот механизм вставки в MS SQL сервер достаточно больших таблиц данных. 2-ым этим парнем на деревне после BULK INSERT был признан механизм вставки через TVP (табличные параметры процедур). Смысл его в том, что на сервере MS SQL создается табличный тип с колонками, идентичными таблице, куда следует поместить данные, к этому типу – хранимая процедура, которая выполняет помещение через Insert, примерно так: CREATE PROCEDURE [dbo].[Create_ MyTable _TVP] ( @ImportTable dbo.Create_ MyTable _TVPStructure READONLY ) AS SET NOCOUNT ON; SET DATEFORMAT dmy; INSERT INTO dbo.MyTable SELECT * FROM @ImportTable; И все идет отлично, скорость офигенная, но до тех пор, пока я не стал передавать тип DateTime2. Firedac стал выкидывать ошибку назависимо от типа драйвера: [FireDAC][Phys][ODBC][Microsoft][SQL Server Native Client 11.0]Переполнение поля Datetime. Точность в долях секунды превышает масштаб, указанный в привязке параметра. [FireDAC][Phys][ODBC][Microsoft][ODBC Driver 17 for SQL Server]Переполнение поля Datetime. Точность в долях секунды превышает масштаб, указанный в привязке параметра. С типом datetime – ситуация – аналогичная. Я перепробовал уже все мыслимое и немыслимое, все настройки Firedac излазил, ничего не помогает. Проблема в том, что Firedac – крайне трудная в отладке ioba, я уже спустился на уровень SQL Binding, но пока не могу найти причину, или даже настройку округления или точности Firedac. Параметр хранимой процедуры я устанавливаю просто как TDataSet, это не скалярный параметр, и никаких настроек для него я задать не могу: FDStoredProc1.ParamByName('@ImportTable').SetDataSet(FDMemTable1, false); Пока, из ситуации, я вышел, передавая строковые представления дат, а в хранимой процедуре делаю обратную конвертацию через Convert(), но это неправильно. Нужна помощь. Тестовый проект на Delphi 11 выложен тут (просто исходники, никаких dcu, dll, exe): https://github.com/Hadgehogs/DemoTFireDacFail Для работы, необходима Delphi 11 (но, скорее всего, пойдет и более ранняя версия), MS SQL 2019 (но возможно подойдет и более ранняя версия) |
9 |
||
1
Garykom
гуру
06.03.23
✎
22:15
|
1. C# вместо Delphi
https://khalidabuhakmeh.com/passing-table-valued-parameters-from-dotnet-to-sql-server 2. Передавай строку и конверти в хранимке |
2 |
||
2
H A D G E H O G s
06.03.23
✎
22:19
|
(1) Ты невнимательно читал. Давай я повторю:
"Пока, из ситуации, я вышел, передавая строковые представления дат, а в хранимой процедуре делаю обратную конвертацию через Convert(), но это неправильно." |
3 |
||
3
Garykom
гуру
06.03.23
✎
22:20
|
(2) Ну и забей на этом
Потому что разбираться в древних и уже хреново поддерживаемых технологиях такое себе |
|||
4
Garykom
гуру
06.03.23
✎
22:22
|
затести еще CAST вместо CONVERT
там формат строки под DataTime2 надо подогнать но возможно будет шустрей |
|||
5
Garykom
гуру
06.03.23
✎
22:32
|
на C# вроде как пашет, если порядок колонок не нарушать
https://stackoverflow.com/questions/8335994/ado-net-table-valued-parameter-tvp-operand-type-clash-datetime2-is-incompati |
|||
6
Кирпич
07.03.23
✎
08:30
|
Вроде написано, что масштаб не тот. какой масштаб у DateTime2 в Delphi и SQLServer?
Тут вабще пишут, что ODBC не понимает DateTime2 https://docwiki.embarcadero.com/RADStudio/Sydney/en/MS_SQL_Server_Questions_(FireDAC) |
9 |
||
7
Кирпич
07.03.23
✎
08:34
|
9 11 |
|||
8
NorthWind
07.03.23
✎
08:46
|
а DBGo (ADO) умерло в свежих версиях дельфи?
|
10 |
||
9
H A D G E H O G s
07.03.23
✎
12:05
|
11 |
|||
10
H A D G E H O G s
07.03.23
✎
12:05
|
(8) Нет.
|
13 |
||
11
Кирпич
07.03.23
✎
12:13
|
12 |
|||
12
H A D G E H O G s
07.03.23
✎
12:13
|
(11) Точно также
|
|||
13
NorthWind
07.03.23
✎
12:14
|
(10) так может, есть попробовать в этом направлении?
Все ж посовременнее чем ODBC |
15 |
||
14
NorthWind
07.03.23
✎
12:15
|
* есть смысл
|
|||
15
H A D G E H O G s
07.03.23
✎
12:21
|
(13) dbGo (AdoStoredProc) не умеет работать с параметрами - табличными частями
|
|||
16
Кирпич
07.03.23
✎
13:06
|
поставь полю тип ftTimeStamp
|
17 18 |
||
17
H A D G E H O G s
07.03.23
✎
13:50
|
(16) Сработало!
|
|||
18
H A D G E H O G s
07.03.23
✎
13:50
|
(16) Это просто попадание наугад или есть инфа или опыт?
|
|||
19
Кирпич
07.03.23
✎
13:51
|
Это гугл
|
20 |
||
20
H A D G E H O G s
07.03.23
✎
13:51
|
(19) Кинь ссылку
|
21 22 |
||
21
XLife
07.03.23
✎
14:20
|
||||
22
Кирпич
07.03.23
✎
15:20
|
24 |
|||
23
Кирпич
07.03.23
✎
15:21
|
Datetime2
SQL_TYPE_TIMESTAMP SQL_TIMESTAMP |
24 |
||
24
H A D G E H O G s
07.03.23
✎
16:00
|
||||
25
Garykom
гуру
07.03.23
✎
16:01
|
Потом потребуется передача бинарных данных (например картинки в базе) и тоже упс
|
26 |
||
26
H A D G E H O G s
07.03.23
✎
16:11
|
(25) Не потребуется. Это парсинг Техжурнала.
|
Форум | Правила | Описание | Объявления | Секции | Поиск | Книга знаний | Вики-миста |