Pytanie jest dość oczywiste. Chcę wykonać proste wyszukiwanie i zamianę, tak jak w edytorze tekstu na danych w kolumnie mojej bazy danych (czyli MsSQL na MS Windows Server 2003)
sql
sql-server
Jiaaro
źródło
źródło
WHERE
?tak jak:
BEGIN TRANSACTION; UPDATE table_name SET column_name=REPLACE(column_name,'text_to_find','replace_with_this'); COMMIT TRANSACTION;
Przykład: zamienia <script ... na <a ..., aby wyeliminować luki w zabezpieczeniach javascript
BEGIN TRANSACTION; UPDATE testdb SET title=REPLACE(title,'script','a'); COMMIT TRANSACTION;
źródło
<script>
tagu, takich jak używanie<style>
lub<object>
tagi lub złośliwesrc
atrybuty lubonerror
atrybuty.To wskazało mi właściwy kierunek, ale mam bazę danych pochodzącą z MSSQL 2000 i nadal używam
ntext
typu danych dla kolumny, w której zastępowałem. Podczas próby uruchomienia polecenia REPLACE na tym typie pojawia się ten błąd:Najprostszym rozwiązaniem, jeśli dane kolumny mieszczą się w obrębie
nvarchar
, jest rzutowanie kolumny podczas zastępowania. Wypożyczenie kodu z zaakceptowanej odpowiedzi :UPDATE YourTable SET Column1 = REPLACE(cast(Column1 as nvarchar(max)),'a','b') WHERE Column1 LIKE '%a%'
To zadziałało idealnie dla mnie. Dzięki temu postowi na forum znalazłem poprawkę. Mam nadzieję, że pomoże to komuś innemu!
źródło
Poniższe instrukcje znajdują i zastępują ciąg w każdej bazie danych (z wyjątkiem systemowych baz danych) w każdej tabeli w instancji, z którą jesteś połączony:
Po prostu zmień
'Search String'
na to, czego szukasz i na'Replace String'
to, czym chcesz to zastąpić.--Getting all the databases and making a cursor DECLARE db_cursor CURSOR FOR SELECT name FROM master.dbo.sysdatabases WHERE name NOT IN ('master','model','msdb','tempdb') -- exclude these databases DECLARE @databaseName nvarchar(1000) --opening the cursor to move over the databases in this instance OPEN db_cursor FETCH NEXT FROM db_cursor INTO @databaseName WHILE @@FETCH_STATUS = 0 BEGIN PRINT @databaseName --Setting up temp table for the results of our search DECLARE @Results TABLE(TableName nvarchar(370), RealColumnName nvarchar(370), ColumnName nvarchar(370), ColumnValue nvarchar(3630)) SET NOCOUNT ON DECLARE @SearchStr nvarchar(100), @ReplaceStr nvarchar(100), @SearchStr2 nvarchar(110) SET @SearchStr = 'Search String' SET @ReplaceStr = 'Replace String' SET @SearchStr2 = QUOTENAME('%' + @SearchStr + '%','''') DECLARE @TableName nvarchar(256), @ColumnName nvarchar(128) SET @TableName = '' --Looping over all the tables in the database WHILE @TableName IS NOT NULL BEGIN DECLARE @SQL nvarchar(2000) SET @ColumnName = '' DECLARE @result NVARCHAR(256) SET @SQL = 'USE ' + @databaseName + ' SELECT @result = MIN(QUOTENAME(TABLE_SCHEMA) + ''.'' + QUOTENAME(TABLE_NAME)) FROM [' + @databaseName + '].INFORMATION_SCHEMA.TABLES WHERE TABLE_TYPE = ''BASE TABLE'' AND TABLE_CATALOG = ''' + @databaseName + ''' AND QUOTENAME(TABLE_SCHEMA) + ''.'' + QUOTENAME(TABLE_NAME) > ''' + @TableName + ''' AND OBJECTPROPERTY( OBJECT_ID( QUOTENAME(TABLE_SCHEMA) + ''.'' + QUOTENAME(TABLE_NAME) ), ''IsMSShipped'' ) = 0' EXEC master..sp_executesql @SQL, N'@result nvarchar(256) out', @result out SET @TableName = @result PRINT @TableName WHILE (@TableName IS NOT NULL) AND (@ColumnName IS NOT NULL) BEGIN DECLARE @ColumnResult NVARCHAR(256) SET @SQL = ' SELECT @ColumnResult = MIN(QUOTENAME(COLUMN_NAME)) FROM [' + @databaseName + '].INFORMATION_SCHEMA.COLUMNS WHERE TABLE_SCHEMA = PARSENAME(''[' + @databaseName + '].' + @TableName + ''', 2) AND TABLE_NAME = PARSENAME(''[' + @databaseName + '].' + @TableName + ''', 1) AND DATA_TYPE IN (''char'', ''varchar'', ''nchar'', ''nvarchar'') AND TABLE_CATALOG = ''' + @databaseName + ''' AND QUOTENAME(COLUMN_NAME) > ''' + @ColumnName + '''' PRINT @SQL EXEC master..sp_executesql @SQL, N'@ColumnResult nvarchar(256) out', @ColumnResult out SET @ColumnName = @ColumnResult PRINT @ColumnName IF @ColumnName IS NOT NULL BEGIN INSERT INTO @Results EXEC ( 'USE ' + @databaseName + ' SELECT ''' + @TableName + ''',''' + @ColumnName + ''',''' + @TableName + '.' + @ColumnName + ''', LEFT(' + @ColumnName + ', 3630) FROM ' + @TableName + ' (NOLOCK) ' + ' WHERE ' + @ColumnName + ' LIKE ' + @SearchStr2 ) END END END --Declaring another temporary table DECLARE @time_to_update TABLE(TableName nvarchar(370), RealColumnName nvarchar(370)) INSERT INTO @time_to_update SELECT TableName, RealColumnName FROM @Results GROUP BY TableName, RealColumnName DECLARE @MyCursor CURSOR; BEGIN DECLARE @t nvarchar(370) DECLARE @c nvarchar(370) --Looping over the search results SET @MyCursor = CURSOR FOR SELECT TableName, RealColumnName FROM @time_to_update GROUP BY TableName, RealColumnName --Getting my variables from the first item OPEN @MyCursor FETCH NEXT FROM @MyCursor INTO @t, @c WHILE @@FETCH_STATUS = 0 BEGIN -- Updating the old values with the new value DECLARE @sqlCommand varchar(1000) SET @sqlCommand = ' USE ' + @databaseName + ' UPDATE [' + @databaseName + '].' + @t + ' SET ' + @c + ' = REPLACE(' + @c + ', ''' + @SearchStr + ''', ''' + @ReplaceStr + ''') WHERE ' + @c + ' LIKE ''' + @SearchStr2 + '''' PRINT @sqlCommand BEGIN TRY EXEC (@sqlCommand) END TRY BEGIN CATCH PRINT ERROR_MESSAGE() END CATCH --Getting next row values FETCH NEXT FROM @MyCursor INTO @t, @c END; CLOSE @MyCursor ; DEALLOCATE @MyCursor; END; DELETE FROM @time_to_update DELETE FROM @Results FETCH NEXT FROM db_cursor INTO @databaseName END CLOSE db_cursor DEALLOCATE db_cursor
Uwaga: to nie jest idealne, ani nie jest zoptymalizowane
źródło
Jeśli pracujesz z SQL Server 2005 lub nowszym, dostępna jest również biblioteka CLR pod adresem http://www.sqlsharp.com/, która zapewnia implementacje .NET funkcji ciągów i wyrażeń RegEx, które w zależności od wolumenu i typu danych mogą być łatwiejsze w użyciu, aw niektórych przypadkach funkcje manipulowania napisami .NET mogą być bardziej wydajne niż funkcje T-SQL.
źródło