Я использовал динамический SQL в своей процедуре SQL Server, я заменил все одинарные кавычки двумя одинарными кавычками перед передачей параметров в мою процедуру. Это предотвращает инъекцию SQL?
Моя процедура, как показано ниже
CREATE PROCEDURE [dbo].[SP_CM_LST_XML]
(@pTable VARCHAR(MAX),
@pColumns VARCHAR(MAX),
@pFilterAndEQ VARCHAR(MAX),
@pFilterAndLK VARCHAR(MAX),
@pFilterOrEQ VARCHAR(MAX),
@pFilterOrLK VARCHAR(MAX),
@pFilterAdditional VARCHAR(MAX),
@pSortField VARCHAR(MAX),
@pDirection VARCHAR(MAX),
@pAdditionalSort VARCHAR(MAX),
@pFromRowno INT,
@pToRowNo INT,
@pDeleted INT,
@pDataType INT,
@pCompany VARCHAR(MAX))
AS
DECLARE @v_sort VARCHAR(MAX) = '';
DECLARE @v_where VARCHAR(MAX) = '';
DECLARE @v_whereAndEQ VARCHAR(MAX) = '';
DECLARE @v_WhereAndLK VARCHAR(MAX) = '';
DECLARE @v_whereOrEQ VARCHAR(MAX) = '';
DECLARE @v_WhereOrLK VARCHAR(MAX) = '';
DECLARE @v_deleted VARCHAR(MAX) = '';
DECLARE @v_Company VARCHAR(MAX) = '';
DECLARE @v_DataType VARCHAR(MAX) = '';
DECLARE @v_sql VARCHAR(MAX) = '';
DECLARE @vIndex int;
BEGIN TRY
DECLARE @idoc INT;
DECLARE @Type VARCHAR(MAX) ='';
DECLARE @Field VARCHAR(MAX) ='';
DECLARE @Value VARCHAR(MAX) ='';
-- Add Filter Condition -- AND + EQUAL
IF LEN(@pFilterAndEQ) > 35
BEGIN
EXEC sp_xml_preparedocument @idoc OUTPUT, @pFilterAndEQ;
DECLARE CurName CURSOR FAST_FORWARD READ_ONLY FOR
SELECT *
FROM OPENXML (@idoc, '/data/row',1) WITH (Type varchar(max), Field varchar(max), Value varchar(max))
OPEN CurName
FETCH NEXT FROM CurName INTO @Type, @Field, @Value
WHILE @@FETCH_STATUS = 0
BEGIN
set @v_whereAndEQ = @v_whereAndEQ + ' AND UPPER(' + @Field + ') = UPPER(''' + @Value + ''')';
FETCH NEXT FROM CurName INTO @Type, @Field, @Value
END
CLOSE CurName
DEALLOCATE CurName
END
-- Add Filter Condition -- AND + LIKE
if LEN(@pFilterAndLK) >35
BEGIN
EXEC sp_xml_preparedocument @idoc OUTPUT, @pFilterAndLK;
DECLARE CurName CURSOR FAST_FORWARD READ_ONLY
FOR SELECT * FROM OPENXML (@idoc, '/data/row',1) WITH (Type varchar(max), Field varchar(max), Value varchar(max))
OPEN CurName
FETCH NEXT FROM CurName INTO @Type, @Field, @Value
WHILE @@FETCH_STATUS = 0
BEGIN
set @v_whereAndLK = @v_whereAndLK + ' AND UPPER(' + @Field + ') LIKE UPPER(''%' + @Value + '%'')';
FETCH NEXT FROM CurName INTO @Type, @Field, @Value
END
CLOSE CurName
DEALLOCATE CurName
END
-- Add Filter Condition -- OR + EQUAL
if LEN(@pFilterOrEQ) >35
BEGIN
EXEC sp_xml_preparedocument @idoc OUTPUT, @pFilterOrEQ;
DECLARE CurName CURSOR FAST_FORWARD READ_ONLY
FOR SELECT * FROM OPENXML (@idoc, '/data/row',1) WITH (Type varchar(max), Field varchar(max), Value varchar(max))
set @vIndex =1;
OPEN CurName
FETCH NEXT FROM CurName INTO @Type, @Field, @Value
WHILE @@FETCH_STATUS = 0
BEGIN
if @vIndex = 1
set @v_WhereOrEQ = @v_WhereOrEQ + ' AND (UPPER(' + @Field + ') = UPPER(''' + @Value + ''')';
else
set @v_WhereOrEQ = @v_WhereOrEQ + ' OR UPPER(' + @Field + ') = UPPER(''' + @Value + ''')';
set @vIndex = @vIndex + 1;
FETCH NEXT FROM CurName INTO @Type, @Field, @Value
END
CLOSE CurName
DEALLOCATE CurName
if LEN(@v_whereOrEQ) > 0
set @v_whereOrEQ = @v_whereOrEQ + ') ';
END
-- Add Filter Condition -- OR + LIKE
if LEN(@pFilterOrLK) >35
BEGIN
EXEC sp_xml_preparedocument @idoc OUTPUT, @pFilterOrLK;
DECLARE CurName CURSOR FAST_FORWARD READ_ONLY
FOR SELECT * FROM OPENXML (@idoc, '/data/row',1) WITH (Type varchar(max), Field varchar(max), Value varchar(max))
set @vIndex =1;
OPEN CurName
FETCH NEXT FROM CurName INTO @Type, @Field, @Value
WHILE @@FETCH_STATUS = 0
BEGIN
if @vIndex = 1
set @v_WhereOrLK = @v_WhereOrLK + ' AND (UPPER(' + @Field + ') LIKE UPPER(''%' + @Value + '%'')';
else
set @v_WhereOrLK = @v_WhereOrLK + ' OR UPPER(' + @Field + ') LIKE UPPER(''%' + @Value + '%'')';
set @vIndex = @vIndex + 1;
FETCH NEXT FROM CurName INTO @Type, @Field, @Value
END
CLOSE CurName
DEALLOCATE CurName
if LEN(@v_WhereOrLK) > 0
set @v_WhereOrLK = @v_WhereOrLK + ') ';
END
IF @pDeleted = 0
set @v_deleted = @v_deleted + ' AND REC_TYPE <> ''5'' ';
set @v_DataType = @v_DataType + ' AND DATA_TYPE = ''' + + ''' ';
IF @pCompany = '0'
set @v_Company = ' AND Created_Comp = ''' + @pCompany + ''' ';
set @v_where = @v_whereAndEQ + ' ' + @v_WhereAndLK + ' ' + @v_whereOrEQ + ' ' + @v_WhereOrLK + ' ';
if @pDirection = '1'
set @v_sort = ' desc ';
else
set @v_sort = ' asc ';
SET @v_sql = 'SELECT * FROM (select row_number() OVER (order by ' + @pSortField + ' ' + @v_sort + ' ' + Convert(varchar(max),@pAdditionalSort) + ') AS DefaultRowIndex, COUNT(*) OVER () AS TotalFiltered, TC.TotalRecord, A.' + @pColumns + ' from ' + @pTable + ' A CROSS APPLY (SELECT count(*) as TotalRecord FROM ' + @pTable + ' where 1 = 1 ' + @v_deleted + ' ' + @v_Company + ') TC WHERE 1 = 1 ' + @v_deleted + ' ' + @v_Company + ' ' + @v_where + @pFilterAdditional + ') TB WHERE TB.DefaultRowIndex >= ' + Convert(varchar(max),@pFromRowno) + ' and TB.DefaultRowIndex <= ' + Convert(varchar(max),@pToRowNo);
EXEC(@v_sql);
END TRY
BEGIN CATCH
END CATCH;
Я использовал строку XML для параметров @pFilterAndEQ, @pFilterAndLK, @pFilterOrEQ и @pFilterOrEQ для обработки столбца динамической таблицы. Параметры как ниже.
<?xml version='1.0' encoding='utf-8' ?><data><row Type="String" Field="Email" Value="test@test.com" /></data>