Po prostu
EXECUTE ('select id from [dbo].[CSVToTable] ('''example@sqldat.com+''')')
declare @listOfIDs varchar(1000);
Albo, co jest lepsze
SET @listOfIDs = '5, 6, 7, 8, 9, 15, 28, 31, 49, 51, 59, 61';
EXECUTE sp_executesql N'select id from [dbo].[CSVToTable] (@listOfIDs)',
N'@listOfIDs VARCHAR(1000)',
@listOfIDs;
- Dlaczego pojawia się ten błąd?
Ponieważ naprawdę przekazujesz za dużo parametrów, więcej niż potrzeba, aby to zrozumieć, uruchom to zapytanie i zobacz, co tak naprawdę przekazujesz do swojej funkcji
SELECT 'select id from [dbo].[CSVToTable] ('example@sqldat.com+')';
który zwróci (i to właśnie próbujesz wykonać)
select id from [dbo].[CSVToTable] (5, 6, 7, 8, 9, 15, 28, 31, 49, 51, 59, 61)
zamiast (czego potrzebujesz)
SELECT 'select id from [dbo].[CSVToTable] ('''example@sqldat.com+''')';
- Ok, ale dlaczego
sp_executesqljest lepszy niżexec?
Po prostu EXEC zmusi Cię do połączenia wszystkich zmiennych w jeden ciąg, to najgorsza rzecz w tym, a to sprawi, że Twój kod będzie w pełni otwarty na wstrzyknięcie SQL . Zobacz Bad Habits to Kick : Using EXEC() instead of sp_executesql
, nie oznacza to, że sp_executesql jest w 100% bezpieczny, ale pozwala na parametryzację wyrażeń podczas gdy EXEC() nie, dlatego jest bezpieczniejszy niż EXEC pod względem wstrzykiwania SQL .
Wreszcie, odkąd oznaczysz
serwer-sql
a nie określasz wersji, sugeruję użycie SPLIT_STRING()
funkcja (2016+) rathar niż twoja, a jeśli nie masz wersji 2016+, stwórz własną bez użycia WHILE pętla, aby uzyskać lepszą wydajność, ponieważ WHILE pętla będzie działać wolno, dlatego należy jej unikać.
Przykłady: