Powershell SMO - 不会返回用户定义的表类型?

时间:2014-03-21 21:27:10

标签: sql-server powershell smo

我试图使用SMO从数据库编写特定对象的脚本(来自Phil Factor - https://www.simple-talk.com/sql/database-administration/automated-script-generation-with-powershell-and-smo/的脚本)。

奇怪的是,用户定义的表格类型不会显示出来。

use YourDatabaseName
CREATE TYPE [dbo].[test_type] AS TABLE(
    id [int] IDENTITY(1,1) NOT NULL)  

现在列出该数据库中的所有对象。请注意,新的表格类型不会显示。有任何想法吗?

$Server = 'yourservername' 
$Database = 'YourDatabaseName'

# Load SMO assembly, and if we are running SQL 2008 DLLs load the SMOExtended and SQLWMIManagement libraries
$v = [System.Reflection.Assembly]::LoadWithPartialName( 'Microsoft.SqlServer.SMO')
if ((($v.FullName.Split(','))[1].Split('='))[1].Split('.')[0] -ne '9') {
    [System.Reflection.Assembly]::LoadWithPartialName('Microsoft.SqlServer.SMOExtended') | out-null
}
[System.Reflection.Assembly]::LoadWithPartialName('Microsoft.SqlServer.SmoEnum') | out-null
set-psdebug -strict # catch a few extra bugs
$ErrorActionPreference = "stop"
$My='Microsoft.SqlServer.Management.Smo'
$srv = new-object ("$My.Server") $Server # attach to the server

$scripter = new-object ("$My.Scripter") $srv # create the scripter
$scripter.Options.AllowSystemObjects = $False
$scripter.Options.DriAll = $True
$scripter.Options.Bindings = $true
$scripter.Options.IncludeDatabaseRoleMemberships = $true

# first we get the bitmap of all the object types we want
$all =[long] [Microsoft.SqlServer.Management.Smo.DatabaseObjectTypes]::all
$srv.databases[$Database].EnumObjects([long]0x1FFFFFFF -band $all) |out-gridview

3 个答案:

答案 0 :(得分:0)

我之前没有像你建议的那样做,但是你可以手动加载一组对象:

    $objectsToScript += $database.Tables
    $objectsToScript += $database.StoredProcedures | where{-not $_.IsEncrypted}
etc...

   $objectsToScript | %{
       $_.Script()
    }

对不起,现在不在带有smo / posh的电脑上。

答案 1 :(得分:0)

我将采取有根据的猜测,用户定义的表类型不包含在[Microsoft.SqlServer.Management.Smo.DatabaseObjectTypes] :: all的枚举中。关于technet的文档没有UserDefinedTableTypes的超文本链接。

您可以从实现UserDefinedTableTypes属性的[Microsoft.SqlServer.Management.SMO.Database]获取正确的信息。我已经尝试过它并且有效。   代码可能不像Phil Factor那样整洁,因为' :: all'是比单独获得属性更好的方法,但可以做到。

答案 2 :(得分:0)

答案是.EnumObjects方法要求您提供所需的所有不同类型的数据库对象的位图。如果像我一样,你决定生命太短暂,你会说“全部”

  [Microsoft.SqlServer.Management.Smo.DatabaseObjectTypes]::all 

SMO似乎没有合理的思考方式。如果您访问的SQL Server版本不支持所有数据库对象类型,则应该耸耸肩并忽略这一事实。哦,不,它费力地出错了,说SQL Server的版本不支持你指定的类型!要解决这个问题,您必须将您想要的枚举一起创建一个位图以传递给该方法。是的,很多枚举,我猜测它在一篇文章中有点令人困惑所以我作弊并且掩盖了我不想要的那些。不幸的是,我必须掩盖用户定义的表类型。因此,在生产系统中,您需要通过将所需列出的所有对象的枚举ORing在一起来完成疼痛障碍。

如今,您可以通过

获取可用的枚举
 [Microsoft.SqlServer.Management.Smo.DatabaseObjectTypes].GetEnumValues()

但要更早地包含早期的PowerShell版本,并获得可以使用的枚举的实际价值

 [enum]::GetValues([Microsoft.SqlServer.Management.Smo.DatabaseObjectTypes]) |  ForEach-Object {"$_ ( $([Convert]::ToString($_.value__, 16)) ) "} 

为您提供每个ENUM的值

ApplicationRole ( 1 ) 
ServiceBroker ( 2 ) 
Default ( 4 ) 
ExtendedStoredProcedure ( 8 ) 
FullTextCatalog ( 10 ) 
MessageType ( 20 ) 
PartitionFunction ( 40 ) 
PartitionScheme ( 80 ) 
DatabaseRole ( 100 ) 
RemoteServiceBinding ( 200 ) 
Rule ( 400 ) 
Schema ( 800 ) 
ServiceContract ( 1000 ) 
ServiceQueue ( 2000 ) 
ServiceRoute ( 4000 ) 
SqlAssembly ( 8000 ) 
StoredProcedure ( 10000 ) 
Synonym ( 20000 ) 
Table ( 40000 ) 
User ( 80000 ) 
UserDefinedAggregate ( 100000 ) 
UserDefinedDataType ( 200000 ) 
UserDefinedFunction ( 400000 ) 
UserDefinedType ( 800000 ) 
View ( 1000000 ) 
XmlSchemaCollection ( 2000000 ) 
SymmetricKey ( 4000000 ) 
Certificate ( 8000000 ) 
AsymmetricKey ( 10000000 ) 
UserDefinedTableTypes ( 20000000 ) 
PlanGuide ( 40000000 ) 
DatabaseEncryptionKey ( 80000000 ) 
DatabaseAuditSpecification ( 100000000 ) 
FullTextStopList ( 200000000 ) 
SearchPropertyList ( 400000000 ) 
Sequence ( 800000000 ) 
Federation ( 1000000000 ) 
All ( 1fffffffff )