2010-08-15 15 views
5

Me gustaría automatizar la generación de scripts (en SSMS -> Tareas -> Generar scripts) en SSMS 2008. He leído que SQL Server 2008 no es compatible con el Asistente de publicación de bases de datos (incluyendo SQLPUBWIZ SCRIPT) pero esta automatización se puede hacer usando SMO en SQL Server 2008. No tengo ni idea sobre SMO y cómo hacer esto usando SMO, así que ¿podría darme algunos consejos (recursos, etc.) sobre cómo comenzar?¿Cómo automatizar la generación de scripts utilizando SMO en SQL Server?

+0

posible duplicado de [Automatizar generar secuencias de comandos Asistente en SQL2008] (http://stackoverflow.com/questions/3380195/automate-generate-scripts-wizard-in-sql2008) O esto también http: // stackoverflow .com/questions/3384649 – gbn

Respuesta

10

La clave para las secuencias de comandos SMO es la clase Scripter. Todas las demás herramientas (como SSMS) utilizan esta clase para los scripts de creación de objetos generados. Hay

{ 
    //Connect to the local, default instance of SQL Server. 
    Server srv = new Server(); 

    //Reference the AdventureWorks2008R2 database. 
    Database db = srv.Databases["AdventureWorks2008R2"]; 

    //Define a Scripter object and set the required scripting options. 
    Scripter scrp = new Scripter(srv); 
    scrp.Options.ScriptDrops = false; 
    scrp.Options.WithDependencies = true; 

    //Iterate through the tables in database and script each one. Display the script. 
    //Note that the StringCollection type needs the System.Collections.Specialized namespace to be included. 
    Microsoft.SqlServer.Management.Sdk.Sfc.Urn[] smoObjects = new Microsoft.SqlServer.Management.Sdk.Sfc.Urn[1] ; 
    foreach (Table tb in db.Tables) { 
     smoObjects[0] = tb.Urn; 
     if (tb.IsSystemObject == false) { 
     System.Collections.Specialized.StringCollection sc; 
     sc = scrp.Script(smoObjects); 
     foreach (string st in sc) { 
      Console.WriteLine(st); 
     } 
     } 
    } 
} 
4

algunas maneras de secuencias de comandos de todos los objetos en la base de datos, pero uno de los más fácil es que la clase tranfer SMO: Hay un ejemplo de uso de MSDN. Aquí hay un código de PowerShell a la escritura a cabo todos los objetos:

add-type -AssemblyName "Microsoft.SqlServer.ConnectionInfo, Version=10.0.0.0, Culture=neutral, PublicKeyToken=89845dcd8080cc91" 
add-type -AssemblyName "Microsoft.SqlServer.Smo, Version=10.0.0.0, Culture=neutral, PublicKeyToken=89845dcd8080cc91" 
add-type -AssemblyName "Microsoft.SqlServer.SMOExtended, Version=10.0.0.0, Culture=neutral, PublicKeyToken=89845dcd8080cc91" 

$sourceSrv = "$env:computername\sql2k8" 
$sourceDb = "Northwind" 

$server = new-object ("Microsoft.SqlServer.Management.Smo.Server") $sourceSrv 
$db = $server.Databases[$sourceDb] 

$transfer = new-object ("Microsoft.SqlServer.Management.Smo.Transfer") $db 
$transfer.CopyAllObjects = $true 
$transfer.DropDestinationObjectsFirst = $true 
$transfer.CopySchema = $true 
$transfer.Options.IncludeIfNotExists = $true 

$transfer.ScriptTransfer() 
7

Aunque la pregunta ha sido respondida con precisión, luché por unos días para armar un guión que el guión a cabo todos los objetos que me importaba en un servidor de base de datos. Aquí está mi código en caso de que sea útil para otra persona en algún momento.

# Load needed assemblies 
[System.Reflection.Assembly]::LoadWithPartialName("Microsoft.SqlServer.SMO") | out-null 
[System.Reflection.Assembly]::LoadWithPartialName("Microsoft.SqlServer.SMOExtended")| Out-Null; 

#Specify target server and databases. 
$sql_server = "SomeServerName" 
$SMOserver = New-Object -TypeName Microsoft.SqlServer.Management.Smo.Server -ArgumentList "$sql_server" 
$databases = $SMOserver.Databases 
$BaseSavePath = "T:\SomeFilePath\" + $sql_server + "\" 

#Remove existing objects. 
Remove-Item $BaseSavePath -Recurse 

#Script server-level objects. 
$ServerSavePath = $BaseSavePath 
$ServerObjects = $SMOserver.BackupDevices 
$ServerObjects += $SMOserver.Endpoints 
$ServerObjects += $SMOserver.JobServer.Jobs 
$ServerObjects += $SMOserver.LinkedServers 
$ServerObjects += $SMOserver.Triggers 

foreach ($ScriptThis in $ServerObjects | where {!($_.IsSystemObject)}) 
{ 
    #Need to Add Some mkDirs for the different $Fldr=$ScriptThis.GetType().Name 
    $scriptr = new-object ('Microsoft.SqlServer.Management.Smo.Scripter') ($SMOserver) 
    $scriptr.Options.AppendToFile = $True 
    $scriptr.Options.AllowSystemObjects = $False 
    $scriptr.Options.ClusteredIndexes = $True 
    $scriptr.Options.DriAll = $True 
    $scriptr.Options.ScriptDrops = $False 
    $scriptr.Options.IncludeHeaders = $False 
    $scriptr.Options.ToFileOnly = $True 
    $scriptr.Options.Indexes = $True 
    $scriptr.Options.Permissions = $True 
    $scriptr.Options.WithDependencies = $False 

    <#Script the Drop too#> 
    $ScriptDrop = new-object ('Microsoft.SqlServer.Management.Smo.Scripter') ($SMOserver) 
    $ScriptDrop.Options.AppendToFile = $True 
    $ScriptDrop.Options.AllowSystemObjects = $False 
    $ScriptDrop.Options.ClusteredIndexes = $True 
    $ScriptDrop.Options.DriAll = $True 
    $ScriptDrop.Options.ScriptDrops = $True 
    $ScriptDrop.Options.IncludeHeaders = $False 
    $ScriptDrop.Options.ToFileOnly = $True 
    $ScriptDrop.Options.Indexes = $True 
    $ScriptDrop.Options.WithDependencies = $False 

    <#This section builds folder structures. Remove the date folder if you want to overwrite#> 
    $TypeFolder=$ScriptThis.GetType().Name 
    if ((Test-Path -Path "$ServerSavePath\$TypeFolder") -eq "true") ` 
      {"Scripting Out $TypeFolder $ScriptThis"} ` 
     else {new-item -type directory -name "$TypeFolder"-path "$ServerSavePath"} 
    $ScriptFile = $ScriptThis -replace ":", "-" -replace "\\", "-" 
    $ScriptDrop.Options.FileName = $ServerSavePath + "\" + $TypeFolder + "\" + $ScriptFile.Replace("]", "").Replace("[", "") + ".sql" 
    $scriptr.Options.FileName = $ServerSavePath + "\" + $TypeFolder + "\" + $ScriptFile.Replace("]", "").Replace("[", "") + ".sql" 

    #This is where each object actually gets scripted one at a time. 
    $ScriptDrop.Script($ScriptThis) 
    $scriptr.Script($ScriptThis) 
} #This ends the object scripting loop at the server level. 


#Script database-level objects. 
foreach ($db in $databases) 
{ 
    $DatabaseObjects = $db.ApplicationRoles 
    $DatabaseObjects += $db.Assemblies 
    $DatabaseObjects += $db.ExtendedStoredProcedures 
    $DatabaseObjects += $db.ExtendedProperties 
    $DatabaseObjects += $db.PartitionFunctions 
    $DatabaseObjects += $db.PartitionSchemes 
    $DatabaseObjects += $db.Roles 
    $DatabaseObjects += $db.Rules 
    $DatabaseObjects += $db.Schemas 
    $DatabaseObjects += $db.StoredProcedures 
    $DatabaseObjects += $db.Synonyms 
    $DatabaseObjects += $db.Tables 
    $DatabaseObjects += $db.Triggers 
    $DatabaseObjects += $db.UserDefinedAggregates 
    $DatabaseObjects += $db.UserDefinedDataTypes 
    $DatabaseObjects += $db.UserDefinedFunctions 
    $DatabaseObjects += $db.UserDefinedTableTypes 
    $DatabaseObjects += $db.UserDefinedTypes 
    $DatabaseObjects += $db.Users 
    $DatabaseObjects += $db.Views 

    #Build this portion of the directory structure out here. Remove the existing directory and its contents first. 
    $DatabaseSavePath = $BaseSavePath + "Databases\" + $db.Name 

    new-item -type directory -path "$DatabaseSavePath" 

    foreach ($ScriptThis in $DatabaseObjects | where {!($_.IsSystemObject)}) 
    { 
     #Need to Add Some mkDirs for the different $Fldr=$ScriptThis.GetType().Name 
     $scriptr = new-object ('Microsoft.SqlServer.Management.Smo.Scripter') ($SMOserver) 
     $scriptr.Options.AppendToFile = $True 
     $scriptr.Options.AllowSystemObjects = $False 
     $scriptr.Options.ClusteredIndexes = $True 
     $scriptr.Options.DriAll = $True 
     $scriptr.Options.ScriptDrops = $False 
     $scriptr.Options.IncludeHeaders = $False 
     $scriptr.Options.ToFileOnly = $True 
     $scriptr.Options.Indexes = $True 
     $scriptr.Options.Permissions = $True 
     $scriptr.Options.WithDependencies = $False 

     <#Script the Drop too#> 
     $ScriptDrop = new-object ('Microsoft.SqlServer.Management.Smo.Scripter') ($SMOserver) 
     $ScriptDrop.Options.AppendToFile = $True 
     $ScriptDrop.Options.AllowSystemObjects = $False 
     $ScriptDrop.Options.ClusteredIndexes = $True 
     $ScriptDrop.Options.DriAll = $True 
     $ScriptDrop.Options.ScriptDrops = $True 
     $ScriptDrop.Options.IncludeHeaders = $False 
     $ScriptDrop.Options.ToFileOnly = $True 
     $ScriptDrop.Options.Indexes = $True 
     $ScriptDrop.Options.WithDependencies = $False 

     <#This section builds folder structures. Remove the date folder if you want to overwrite#> 
     $TypeFolder=$ScriptThis.GetType().Name 
     if ((Test-Path -Path "$DatabaseSavePath\$TypeFolder") -eq "true") ` 
       {"Scripting Out $TypeFolder $ScriptThis"} ` 
      else {new-item -type directory -name "$TypeFolder"-path "$DatabaseSavePath"} 
     $ScriptFile = $ScriptThis -replace ":", "-" -replace "\\", "-" 
     $ScriptDrop.Options.FileName = $DatabaseSavePath + "\" + $TypeFolder + "\" + $ScriptFile.Replace("]", "").Replace("[", "") + ".sql" 
     $scriptr.Options.FileName = $DatabaseSavePath + "\" + $TypeFolder + "\" + $ScriptFile.Replace("]", "").Replace("[", "") + ".sql" 

     #This is where each object actually gets scripted one at a time. 
     $ScriptDrop.Script($ScriptThis) 
     $scriptr.Script($ScriptThis) 

    } #This ends the object scripting loop. 
} #This ends the database loop. 
Cuestiones relacionadas