SQLServerCentral Article

SMO Basics

,

Over the past few years I've written a few articles on using DMO and I've used it for a lot of small projects with good success. If you come from a development background working with objects and collections is often more intuitive than trying to figure out all the system tables/views you need to query to accomplish a given task. Now that SQL 2005 is here the management objects have been upgraded to reflect the new server as well as using the .Net framework. As I write that it occurs to me that not everyone reading this will be well grounded in objects - look for a future article that covers that in more detail. For now, I'm hoping you can paste this code into your IDE and start to see how it works.

First thing is to make sure you have SMO installed. An easy way to check is to select Project, References in the IDE and look for 'Microsoft.SQLServer.SMO'. If you don't see it you'll need to run the SQL install to get it added. You'll also need a copy of Visual Studio 2005 (any of the many versions) loaded.

Today we're trying to our feet wet with SMO. I've commented the code some to help you walk through it when you get there, but I want to talk through it first. The first real line of code is the one that contains 'Oserver = New Smo.SQLServer ("localhost"). That's where we establish a trusted (NT) connection to the server and is logically just about the top of the heap - the server object will contain databases that in turn contain tables, etc. Very similar to DMO thus far.

In DMO you could pass a variety of flags to the script method that would customize the output, I pulled this sample from one of the older articles. You can see that we're passing in a total of four flags (named constants) by adding them together to get one value. Inside DMO it will decode them back to their separate values.

'SQLDMOScript_AppendToFile=8192

        'SQLDMOScript_ObjectPermissions=2

        'SQLDMOScript_ToFileOnly=64

        'SQLDMOScript_PrimaryObject=4

        oView.Script 8192 + 2 + 64 + 4, "C:\DMO_Views_" &

oDatabase.Name & ".sql"

SMO changes the game slightly. Instead of adding up the values of the different flags and passing them in, we're going to create an Options object and set properties as needed. I don't know that it's better than before, just different. To give you a feel for how it works I only set one property, ScriptDrops, to true. When you look at the output you'll see it has created a drop database statement. You can experiment with this by setting it to false and seeing the drop omitted, or change it to some other property and seeing how it affects the results. Once we've configured our Options object we pass it as a parameter to the Database script method.

Another difference is that DMO returned or output the script as a string. SMO does so indirectly, returning all the statements needed for that particular script into a collection (think super array). To get all the statements we will have to loop through the collection and in this case just output them to the debug window, though of course you could write them to a file or just execute them.

Further down you'll see code that begins with 'For Each oTable in'. This is demonstrating how to iterate through all the tables in the master database, identify those that start with SPT_F, and then script the create statements for them. Notice that this time I didn't pass in the Options object. It's an optional option! Below is the source code, I'm also including it here so you can  download and work with it easily. Further down is the output copied from the debug window when I ran it on my machine. Nothing in the code below will change the state of your machine, but please do experiment on a local instance that can be easily reloaded if you break something experimenting.

Imports Microsoft.SqlServer.Management
Public Class Form1
    Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        '6/13/06 Andy Warren/SQLServerCentral.com
        'Sample code to demonstrate scripting in SMO
        Dim oServer As Smo.Server
        Dim Scripts As System.Collections.Specialized.StringCollection
        Dim Options As Smo.ScriptingOptions
        Dim oTable As Smo.Table
        Try
            'connect to local default instance, assumes NT authentication
            oServer = New Smo.Server("localhost")
            'options are flags that tell SMO how to script an object, similar to the flags you'd pass in DMO
            Options = New Smo.ScriptingOptions
            'this one will create the "drop database" statement because its set to true
            Options.ScriptDrops = True
            'now we'll point it a database we know we have, in this case the master db. It will return
            'a collection of TSQL statements we would execute to recreate the database (the mdf/ldf, not all the
            'contents. From here we could write to a file, execute, view, whatever.
            Scripts = oServer.Databases("master").Script(Options)
            'this will dump to the debug window
            For Each S As String In Scripts
                Debug.Print(S.ToString)
            Next
            'now lets look at scripting a bunch of objects, in this case all the tables that start with 'SPT_F'
            'just to show how to do a conditional. As we find each table we send the results to the Scripts
            'string collection, then just as before loop through it to write out the individual TSQL statements
            For Each oTable In oServer.Databases("master").Tables
                If oTable.Name.ToUpper Like "SPT_F*" Then
                    Scripts = oTable.Script
                    For Each S As String In Scripts
                        Debug.Print(S.ToString)
                    Next
                End If
            Next
        Catch ex As Exception
            MessageBox.Show(ex.ToString)
        Finally
            Options = Nothing
            oServer = Nothing
        End Try
    End Sub
End Class
CREATE DATABASE [master] ON  PRIMARY 
( NAME = N'master', FILENAME = N'C:\Program Files\Microsoft SQL Server\MSSQL.1\MSSQL\DATA\master.mdf' , SIZE = 4096KB , MAXSIZE = UNLIMITED, FILEGROWTH = 10%)
 LOG ON 
( NAME = N'mastlog', FILENAME = N'C:\Program Files\Microsoft SQL Server\MSSQL.1\MSSQL\DATA\mastlog.ldf' , SIZE = 512KB , MAXSIZE = UNLIMITED, FILEGROWTH = 10%)
 COLLATE SQL_Latin1_General_CP1_CI_AS
EXEC dbo.sp_dbcmptlevel @dbname=N'master', @new_cmptlevel=90
IF (1 = FULLTEXTSERVICEPROPERTY('IsFullTextInstalled'))
begin
EXEC [master].[dbo].[sp_fulltext_database] @action = 'disable'
end
ALTER DATABASE [master] SET ANSI_NULL_DEFAULT OFF 
ALTER DATABASE [master] SET ANSI_NULLS OFF 
ALTER DATABASE [master] SET ANSI_PADDING OFF 
ALTER DATABASE [master] SET ANSI_WARNINGS OFF 
ALTER DATABASE [master] SET ARITHABORT OFF 
ALTER DATABASE [master] SET AUTO_CLOSE OFF 
ALTER DATABASE [master] SET AUTO_CREATE_STATISTICS ON 
ALTER DATABASE [master] SET AUTO_SHRINK OFF 
ALTER DATABASE [master] SET AUTO_UPDATE_STATISTICS ON 
ALTER DATABASE [master] SET CURSOR_CLOSE_ON_COMMIT OFF 
ALTER DATABASE [master] SET CURSOR_DEFAULT  GLOBAL 
ALTER DATABASE [master] SET CONCAT_NULL_YIELDS_NULL OFF 
ALTER DATABASE [master] SET NUMERIC_ROUNDABORT OFF 
ALTER DATABASE [master] SET QUOTED_IDENTIFIER OFF 
ALTER DATABASE [master] SET RECURSIVE_TRIGGERS OFF 
ALTER DATABASE [master] SET  DISABLE_BROKER 
ALTER DATABASE [master] SET AUTO_UPDATE_STATISTICS_ASYNC OFF 
ALTER DATABASE [master] SET DATE_CORRELATION_OPTIMIZATION OFF 
ALTER DATABASE [master] SET TRUSTWORTHY OFF 
ALTER DATABASE [master] SET ALLOW_SNAPSHOT_ISOLATION ON 
ALTER DATABASE [master] SET PARAMETERIZATION SIMPLE 
ALTER DATABASE [master] SET  READ_WRITE 
ALTER DATABASE [master] SET RECOVERY SIMPLE 
ALTER DATABASE [master] SET  MULTI_USER 
ALTER DATABASE [master] SET PAGE_VERIFY CHECKSUM  
ALTER DATABASE [master] SET DB_CHAINING ON 
SET ANSI_NULLS ON
SET QUOTED_IDENTIFIER ON
CREATE TABLE [dbo].[spt_fallback_db](
[xserver_name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[xdttm_ins] [datetime] NOT NULL,
[xdttm_last_ins_upd] [datetime] NOT NULL,
[xfallback_dbid] [smallint] NULL,
[name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[dbid] [smallint] NOT NULL,
[status] [smallint] NOT NULL,
[version] [smallint] NOT NULL
) ON [PRIMARY]
SET ANSI_NULLS ON
SET QUOTED_IDENTIFIER ON
CREATE TABLE [dbo].[spt_fallback_dev](
[xserver_name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[xdttm_ins] [datetime] NOT NULL,
[xdttm_last_ins_upd] [datetime] NOT NULL,
[xfallback_low] [int] NULL,
[xfallback_drive] [char](2) COLLATE SQL_Latin1_General_CP1_CI_AS NULL,
[low] [int] NOT NULL,
[high] [int] NOT NULL,
[status] [smallint] NOT NULL,
[name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[phyname] [varchar](127) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL
) ON [PRIMARY]
SET ANSI_NULLS ON
SET QUOTED_IDENTIFIER ON
CREATE TABLE [dbo].[spt_fallback_usg](
[xserver_name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[xdttm_ins] [datetime] NOT NULL,
[xdttm_last_ins_upd] [datetime] NOT NULL,
[xfallback_vstart] [int] NULL,
[dbid] [smallint] NOT NULL,
[segmap] [int] NOT NULL,
[lstart] [int] NOT NULL,
[sizepg] [int] NOT NULL,
[vstart] [int] NOT NULL
) ON [PRIMARY]
DROP DATABASE [master]
SET ANSI_NULLS ON
SET QUOTED_IDENTIFIER ON
CREATE TABLE [dbo].[spt_fallback_db](
[xserver_name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[xdttm_ins] [datetime] NOT NULL,
[xdttm_last_ins_upd] [datetime] NOT NULL,
[xfallback_dbid] [smallint] NULL,
[name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[dbid] [smallint] NOT NULL,
[status] [smallint] NOT NULL,
[version] [smallint] NOT NULL
) ON [PRIMARY]
SET ANSI_NULLS ON
SET QUOTED_IDENTIFIER ON
CREATE TABLE [dbo].[spt_fallback_dev](
[xserver_name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[xdttm_ins] [datetime] NOT NULL,
[xdttm_last_ins_upd] [datetime] NOT NULL,
[xfallback_low] [int] NULL,
[xfallback_drive] [char](2) COLLATE SQL_Latin1_General_CP1_CI_AS NULL,
[low] [int] NOT NULL,
[high] [int] NOT NULL,
[status] [smallint] NOT NULL,
[name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[phyname] [varchar](127) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL
) ON [PRIMARY]
SET ANSI_NULLS ON
SET QUOTED_IDENTIFIER ON
CREATE TABLE [dbo].[spt_fallback_usg](
[xserver_name] [varchar](30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL,
[xdttm_ins] [datetime] NOT NULL,
[xdttm_last_ins_upd] [datetime] NOT NULL,
[xfallback_vstart] [int] NULL,
[dbid] [smallint] NOT NULL,
[segmap] [int] NOT NULL,
[lstart] [int] NOT NULL,
[sizepg] [int] NOT NULL,
[vstart] [int] NOT NULL
) ON [PRIMARY]

Rate

You rated this post out of 5. Change rating

Share

Share

Rate

You rated this post out of 5. Change rating