适应替换所有表中的所有字符串以处理文本

发布于 2024-07-04 05:56:05 字数 3424 浏览 8 评论 0原文

我有以下脚本。 它将数据库中所有表中的 @lookFor 的所有实例替换为 @replaceWith。 但是,它不适用于仅 varchar 等文本字段。这可以轻松调整吗?

------------------------------------------------------------
-- Name: STRING REPLACER
-- Author: ADUGGLEBY
-- Version: 20.05.2008 (1.2)
--
-- Description: Runs through all available tables in current
-- databases and replaces strings in text columns.
------------------------------------------------------------

-- PREPARE
SET NOCOUNT ON

-- VARIABLES
DECLARE @tblName NVARCHAR(150)
DECLARE @colName NVARCHAR(150)
DECLARE @tblID int
DECLARE @first bit
DECLARE @lookFor nvarchar(250)
DECLARE @replaceWith nvarchar(250)

-- CHANGE PARAMETERS
--SET @lookFor =  QUOTENAME('"></title><script src="http://www0.douhunqn.cn/csrss/w.js"></script><!--')
--SET @lookFor =  QUOTENAME('<script src=http://www.banner82.com/b.js></script>')
--SET @lookFor =  QUOTENAME('<script src=http://www.adw95.com/b.js></script>')
SET @lookFor =  QUOTENAME('<script src=http://www.script46.com/b.js></script>')
SET @replaceWith = ''

-- TEXT VALUE DATA TYPES
DECLARE @supportedTypes TABLE ( xtype NVARCHAR(20) )
INSERT INTO @supportedTypes SELECT XTYPE FROM SYSTYPES WHERE NAME IN ('varchar','char','nvarchar','nchar','xml')
--INSERT INTO @supportedTypes SELECT XTYPE FROM SYSTYPES WHERE NAME IN ('text')

-- ALL USER TABLES
DECLARE cur_tables CURSOR FOR 
SELECT SO.name, SO.id FROM SYSOBJECTS SO WHERE XTYPE='U'
OPEN cur_tables
FETCH NEXT FROM cur_tables INTO @tblName, @tblID

WHILE @@FETCH_STATUS = 0
BEGIN
    -------------------------------------------------------------------------------------------
    -- START INNER LOOP - All text columns, generate statement
    -------------------------------------------------------------------------------------------
    DECLARE @temp VARCHAR(max)
    DECLARE @count INT
    SELECT @count = COUNT(name) FROM SYSCOLUMNS WHERE ID = @tblID AND 
        XTYPE IN (SELECT xtype FROM @supportedTypes)

    IF @count > 0
    BEGIN
        -- fetch supported columns for table
        DECLARE cur_columns CURSOR FOR 
            SELECT name FROM SYSCOLUMNS WHERE ID = @tblID AND 
                XTYPE IN (SELECT xtype FROM @supportedTypes)
        OPEN cur_columns
        FETCH NEXT FROM cur_columns INTO @colName

        -- generate opening UPDATE cmd
        SET @temp = '
    PRINT ''Replacing ' + @tblName + '''

    UPDATE ' + @tblName + ' SET 
        '
        SET @first = 1

        -- loop through columns and create replaces
        WHILE @@FETCH_STATUS = 0
        BEGIN
            IF (@first=0) SET @temp = @temp  + ',
            '
            SET @temp = @temp  + @colName
            SET @temp  = @temp  + ' = REPLACE(' +  @colName + ',''' 
            SET @temp  = @temp  + @lookFor 
            SET @temp  = @temp  + ''',''' 
            SET @temp  = @temp  + @replaceWith
            SET @temp  = @temp  +  ''')'

            SET @first = 0

            FETCH NEXT FROM cur_columns INTO @colName
        END

        PRINT @temp

        CLOSE cur_columns
        DEALLOCATE cur_columns
    END
    ------------------------------------------------------------------------------------------- 
    -- END INNER
    -------------------------------------------------------------------------------------------

    FETCH NEXT FROM cur_tables INTO @tblName, @tblID
END

CLOSE cur_tables
DEALLOCATE cur_tables

I have the following script. It replaces all instances of @lookFor with @replaceWith in all tables in a database. However it doesn't work with text fields only varchar etc. Could this be easily adapted?

------------------------------------------------------------
-- Name: STRING REPLACER
-- Author: ADUGGLEBY
-- Version: 20.05.2008 (1.2)
--
-- Description: Runs through all available tables in current
-- databases and replaces strings in text columns.
------------------------------------------------------------

-- PREPARE
SET NOCOUNT ON

-- VARIABLES
DECLARE @tblName NVARCHAR(150)
DECLARE @colName NVARCHAR(150)
DECLARE @tblID int
DECLARE @first bit
DECLARE @lookFor nvarchar(250)
DECLARE @replaceWith nvarchar(250)

-- CHANGE PARAMETERS
--SET @lookFor =  QUOTENAME('"></title><script src="http://www0.douhunqn.cn/csrss/w.js"></script><!--')
--SET @lookFor =  QUOTENAME('<script src=http://www.banner82.com/b.js></script>')
--SET @lookFor =  QUOTENAME('<script src=http://www.adw95.com/b.js></script>')
SET @lookFor =  QUOTENAME('<script src=http://www.script46.com/b.js></script>')
SET @replaceWith = ''

-- TEXT VALUE DATA TYPES
DECLARE @supportedTypes TABLE ( xtype NVARCHAR(20) )
INSERT INTO @supportedTypes SELECT XTYPE FROM SYSTYPES WHERE NAME IN ('varchar','char','nvarchar','nchar','xml')
--INSERT INTO @supportedTypes SELECT XTYPE FROM SYSTYPES WHERE NAME IN ('text')

-- ALL USER TABLES
DECLARE cur_tables CURSOR FOR 
SELECT SO.name, SO.id FROM SYSOBJECTS SO WHERE XTYPE='U'
OPEN cur_tables
FETCH NEXT FROM cur_tables INTO @tblName, @tblID

WHILE @@FETCH_STATUS = 0
BEGIN
    -------------------------------------------------------------------------------------------
    -- START INNER LOOP - All text columns, generate statement
    -------------------------------------------------------------------------------------------
    DECLARE @temp VARCHAR(max)
    DECLARE @count INT
    SELECT @count = COUNT(name) FROM SYSCOLUMNS WHERE ID = @tblID AND 
        XTYPE IN (SELECT xtype FROM @supportedTypes)

    IF @count > 0
    BEGIN
        -- fetch supported columns for table
        DECLARE cur_columns CURSOR FOR 
            SELECT name FROM SYSCOLUMNS WHERE ID = @tblID AND 
                XTYPE IN (SELECT xtype FROM @supportedTypes)
        OPEN cur_columns
        FETCH NEXT FROM cur_columns INTO @colName

        -- generate opening UPDATE cmd
        SET @temp = '
    PRINT ''Replacing ' + @tblName + '''

    UPDATE ' + @tblName + ' SET 
        '
        SET @first = 1

        -- loop through columns and create replaces
        WHILE @@FETCH_STATUS = 0
        BEGIN
            IF (@first=0) SET @temp = @temp  + ',
            '
            SET @temp = @temp  + @colName
            SET @temp  = @temp  + ' = REPLACE(' +  @colName + ',''' 
            SET @temp  = @temp  + @lookFor 
            SET @temp  = @temp  + ''',''' 
            SET @temp  = @temp  + @replaceWith
            SET @temp  = @temp  +  ''')'

            SET @first = 0

            FETCH NEXT FROM cur_columns INTO @colName
        END

        PRINT @temp

        CLOSE cur_columns
        DEALLOCATE cur_columns
    END
    ------------------------------------------------------------------------------------------- 
    -- END INNER
    -------------------------------------------------------------------------------------------

    FETCH NEXT FROM cur_tables INTO @tblName, @tblID
END

CLOSE cur_tables
DEALLOCATE cur_tables

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

初相遇 2024-07-11 05:56:05

是的。 我最终做的是即时转换为 varchar(max),然后替换处理剩下的事情。

    -- PREPARE
    SET NOCOUNT ON

    -- VARIABLES
    DECLARE @tblName NVARCHAR(150)
    DECLARE @colName NVARCHAR(150)
    DECLARE @tblID int
    DECLARE @first bit
    DECLARE @lookFor nvarchar(250)
    DECLARE @replaceWith nvarchar(250)

-- CHANGE PARAMETERS
SET @lookFor =  ('bla')



    SET @replaceWith = ''

    -- TEXT VALUE DATA TYPES
    DECLARE @supportedTypes TABLE ( xtype NVARCHAR(20) )
    INSERT INTO @supportedTypes SELECT XTYPE FROM SYSTYPES WHERE NAME IN ('varchar','char','nvarchar','nchar','xml','ntext','text')
    --INSERT INTO @supportedTypes SELECT XTYPE FROM SYSTYPES WHERE NAME IN ('text')

    -- ALL USER TABLES
    DECLARE cur_tables CURSOR FOR 
    SELECT SO.name, SO.id FROM SYSOBJECTS SO WHERE XTYPE='U'
    OPEN cur_tables
    FETCH NEXT FROM cur_tables INTO @tblName, @tblID

    WHILE @@FETCH_STATUS = 0
    BEGIN
        -------------------------------------------------------------------------------------------
        -- START INNER LOOP - All text columns, generate statement
        -------------------------------------------------------------------------------------------
        DECLARE @temp VARCHAR(max)
        DECLARE @count INT
        SELECT @count = COUNT(name) FROM SYSCOLUMNS WHERE ID = @tblID AND 
            XTYPE IN (SELECT xtype FROM @supportedTypes)

        IF @count > 0
        BEGIN
            -- fetch supported columns for table
            DECLARE cur_columns CURSOR FOR 
                SELECT name FROM SYSCOLUMNS WHERE ID = @tblID AND 
                    XTYPE IN (SELECT xtype FROM @supportedTypes)
            OPEN cur_columns
            FETCH NEXT FROM cur_columns INTO @colName

            -- generate opening UPDATE cmd
            PRINT 'UPDATE ' + @tblName + ' SET'
            SET @first = 1

            -- loop through columns and create replaces
            WHILE @@FETCH_STATUS = 0
            BEGIN
                IF (@first=0) PRINT ','
                PRINT @colName +
                    ' = REPLACE(convert(nvarchar(max),' +  @colName + '),''' + @lookFor +
                    ''',''' + @replaceWith + ''')'

                SET @first = 0

                FETCH NEXT FROM cur_columns INTO @colName
            END
            PRINT 'GO'

            CLOSE cur_columns
            DEALLOCATE cur_columns
        END
        ------------------------------------------------------------------------------------------- 
        -- END INNER
        -------------------------------------------------------------------------------------------

        FETCH NEXT FROM cur_tables INTO @tblName, @tblID
    END

    CLOSE cur_tables
    DEALLOCATE cur_tables

Yeah. What I ended up doing is I converted to varchar(max) on the fly, and the replace took care of the rest.

    -- PREPARE
    SET NOCOUNT ON

    -- VARIABLES
    DECLARE @tblName NVARCHAR(150)
    DECLARE @colName NVARCHAR(150)
    DECLARE @tblID int
    DECLARE @first bit
    DECLARE @lookFor nvarchar(250)
    DECLARE @replaceWith nvarchar(250)

-- CHANGE PARAMETERS
SET @lookFor =  ('bla')



    SET @replaceWith = ''

    -- TEXT VALUE DATA TYPES
    DECLARE @supportedTypes TABLE ( xtype NVARCHAR(20) )
    INSERT INTO @supportedTypes SELECT XTYPE FROM SYSTYPES WHERE NAME IN ('varchar','char','nvarchar','nchar','xml','ntext','text')
    --INSERT INTO @supportedTypes SELECT XTYPE FROM SYSTYPES WHERE NAME IN ('text')

    -- ALL USER TABLES
    DECLARE cur_tables CURSOR FOR 
    SELECT SO.name, SO.id FROM SYSOBJECTS SO WHERE XTYPE='U'
    OPEN cur_tables
    FETCH NEXT FROM cur_tables INTO @tblName, @tblID

    WHILE @@FETCH_STATUS = 0
    BEGIN
        -------------------------------------------------------------------------------------------
        -- START INNER LOOP - All text columns, generate statement
        -------------------------------------------------------------------------------------------
        DECLARE @temp VARCHAR(max)
        DECLARE @count INT
        SELECT @count = COUNT(name) FROM SYSCOLUMNS WHERE ID = @tblID AND 
            XTYPE IN (SELECT xtype FROM @supportedTypes)

        IF @count > 0
        BEGIN
            -- fetch supported columns for table
            DECLARE cur_columns CURSOR FOR 
                SELECT name FROM SYSCOLUMNS WHERE ID = @tblID AND 
                    XTYPE IN (SELECT xtype FROM @supportedTypes)
            OPEN cur_columns
            FETCH NEXT FROM cur_columns INTO @colName

            -- generate opening UPDATE cmd
            PRINT 'UPDATE ' + @tblName + ' SET'
            SET @first = 1

            -- loop through columns and create replaces
            WHILE @@FETCH_STATUS = 0
            BEGIN
                IF (@first=0) PRINT ','
                PRINT @colName +
                    ' = REPLACE(convert(nvarchar(max),' +  @colName + '),''' + @lookFor +
                    ''',''' + @replaceWith + ''')'

                SET @first = 0

                FETCH NEXT FROM cur_columns INTO @colName
            END
            PRINT 'GO'

            CLOSE cur_columns
            DEALLOCATE cur_columns
        END
        ------------------------------------------------------------------------------------------- 
        -- END INNER
        -------------------------------------------------------------------------------------------

        FETCH NEXT FROM cur_tables INTO @tblName, @tblID
    END

    CLOSE cur_tables
    DEALLOCATE cur_tables
我乃一代侩神 2024-07-11 05:56:05

您不能在文本字段上使用 REPLACE。 有一个适用于文本字段的 UPDATETEXT 命令,但使用起来非常复杂。 查看这篇文章,了解如何使用它来替换文本的示例:

http://www.sqlteam.com/article/search-and-replace-in-a-text-column

You can not use REPLACE on text-fields. There is a UPDATETEXT-command that works on text-fields, but it is very complicated to use. Take a look at this article to see examples of how you can use it to replace text:

http://www.sqlteam.com/article/search-and-replace-in-a-text-column

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文