Technical Article

Find and replace column constraints

,

I submit this script as an example of how one might go about generating 'Alter Table' statements that find and replace specific column constraints. In my case I had to find all occurrences in a production db of suser_name() as a column constraint and replace it with suser_sname(). This script is only an example and does not fix any table directly. It only generates the 'Alter Table' statements which can then be saved and run at a later date.

-- Set nocount and declare variables.
Set nocount on
Declare @tblname sysname,
        @owner sysname,
        @objname sysname,
        @ConstTxttoFind varchar(128),
        @ConstTxtFix varchar(128),
        @ColumnMatch sysname

-- Set some initial values.
Set @ConstTxttoFind = '(suser_name())' 
Set @ConstTxtFix = 'suser_sname()'
Set @ColumnMatch = '%user%'

-- Create some temporary holding tables.
If (Select object_id('tempdb.dbo.#tbllist')) > 0
   Exec ('Drop table #tbllist')

Create table #tbllist(
   tblname sysname null,
   owner   sysname null,
   objname sysname null)

If (Select object_id('tempdb.dbo.#commands')) > 0
   Exec ('Drop table #commands')

Create table #commands(
   [--value] varchar(4096) null)

-- Retrieve a unique list of user tables by owner.
Insert into #tbllist
Select a.name, 
       b.name, 
       convert(sysname, b.name + '.' + a.name)
  from sysobjects a
  join sysusers b
    on a.uid = b.uid
 where a.type = 'U'

-- Add some output set commands if needed.
--Print 'BEGIN TRANSACTION'
--Print 'SET QUOTED_IDENTIFIER ON'
--Print 'SET TRANSACTION ISOLATION LEVEL SERIALIZABLE'
--Print 'SET ARITHABORT ON'
--Print 'SET NUMERIC_ROUNDABORT OFF'
--Print 'SET CONCAT_NULL_YIELDS_NULL ON'
--Print 'SET ANSI_NULLS ON'
--Print 'SET ANSI_PADDING ON'
--Print 'SET ANSI_WARNINGS ON'
--Print 'COMMIT'
--Print ''

-- Get the first unique owner.table name for the loop.
Select @objname = min(objname) 
  from #tbllist

-- Begin the loop and loop until all tables have been processed
While @objname is not null
   Begin
      -- Retrieve individual table and owner info.
      Select @tblname = tblname, @owner = owner from #tbllist where @objname = objname

      -- Load the Temp table with the 'Alter Table' statements.
      Insert into #commands
      Select char(13) + char(10) + 'Begin transaction ' + char(13) + char(10) +
             'Alter table ' + @objname + char(13) + char(10) +
             '   Drop Constraint ' + f.name + char(13) + char(10)+  
             'Alter table ' + @objname + ' Add Constraint ' + char(13) + char(10) +
             '   ' + f.name + ' Default ' + @ConstTxtFix + ' For ' + b.name + 
             char(13) + char(10) + 'If @@error > 0 Begin Print @@error Rollback End Else Commit' +
             char(13) + char(10) + 'Go' 
      --Select a.name, b.name, f.name, convert(varchar(50),g.text) -- for test
        from sysobjects a 
        join syscolumns b 
          on a.id = b.id 
        join systypes c 
          on b.xusertype = c.xusertype 
        join sysusers d 
          on a.uid = d.uid 
        left outer join (Apollo2.dbo.sysconstraints e 
                            join sysobjects f 
                              on e.constid = f.id 
                             and e.status&0xf = 5 
                            join syscomments g 
                              on g.id = f.id) 
          on b.id = e.id 
         and b.colid = e.colid 
      where a.name = @tblname
        and d.name = @owner
        and b.name like @ColumnMatch
        and g.text = @ConstTxttoFind

      -- Get the next unique owner.table name.
      Select @objname = min(objname) 
        from #tbllist 
       where objname > @objname
   End

-- Display the results.
Select * from #commands
Select '-- ' + str(@@rowcount)
Go


/*  -- Results
Begin transaction 
Alter table dbo.alt_title
   Drop Constraint DF__alt_title__creat__114A936A
Alter table dbo.alt_title Add Constraint 
   DF__alt_title__creat__114A936A Default suser_sname() For creation_user
If @@error > 0 Begin Print @@error Rollback End Else Commit
--Go

-- I had 165 changes generated this way
*/

Rate

You rated this post out of 5. Change rating

Share

Share

Rate

You rated this post out of 5. Change rating