如何获取.MDF数据库的内部SQL Server数据库版本号?

时间:2013-04-23 14:20:20

标签: sql-server vb.net

我想以编程方式获取SQL Server数据库的内部数据库版本号,以确定要使用的SQL Server实例。

即。 SQL Server 2008 - 版本661,SQL Server 2008 R2 - 版本665

我找到了一篇文章:http://rusanu.com/2011/04/04/how-to-determine-the-database-version-of-an-mdf-file/,它将版本号的位置显示为.mdf文件中偏移量为0×12064的DWORD值。

如何以编程方式获取此信息?

由于

2 个答案:

答案 0 :(得分:0)

如果已附加数据库:

CREATE TABLE #d
(
  ParentObject NVARCHAR(4000),
  [Object] NVARCHAR(4000),
  Field NVARCHAR(4000),
  VALUE NVARCHAR(4000)
);

DECLARE @sql NVARCHAR(MAX) = N'dbcc page(' + RTRIM(DB_ID()) 
  + ',1,9,3) with tableresults;'

INSERT #d EXEC sp_executesql @sql;

SELECT [Version] = VALUE FROM #d WHERE Field = N'dbi_version';

DROP TABLE #d;

虽然数据库已经附加,但它已经是实例的版本。如果未附加数据库,为什么不将它附加到您拥有的最新版本?仅仅因为数据库目前是661并不意味着它必须保持这种状态。如果您将其附加到2008 R2或2012也可以使用。

答案 1 :(得分:0)

这是我创建的存储过程,用于使用OLE自动化和ADO的Stream对象读取脱机.mdf。此解决方案和更多上下文也会发布在此处:https://social.technet.microsoft.com/Forums/sqlserver/en-US/3de5b574-0751-44a2-b69f-fa0c20378359/how-to-determine-sql-server-version-of-an-mdf-file?forum=sqlsetupandupgrade

CREATE /*ALTER*/ PROCEDURE spDBVersion
(
@FilePath nvarchar(500) /*Your filepath here EG 'C:\SQLData\somedatabase.mdf'*/
)
AS

DECLARE @HR int,
        @objStream int,
        @strErrorMessage Varchar(1000),
        @Source nvarchar(255),
        @Desc nvarchar(255),
        @offset bigint,
        @binary1 binary,
        @binary2 binary

SET NOCOUNT ON

SELECT @strErrorMessage='Creating ADO stream object'
EXEC @HR = sp_OACreate  'ADODB.Stream' , @objStream OUT
IF @HR <> 0 GOTO CLEANUP

SELECT @strErrorMessage='Opening ADO stream'
EXEC @HR = sp_OAMethod @objStream, 'Open'
IF @HR <> 0 GOTO CLEANUP

SELECT @strErrorMessage='Declaring ADO stream type binary'
EXEC @HR = sp_OASetProperty @objStream, 'Type', 1
IF @HR <> 0 GOTO CLEANUP

SELECT @strErrorMessage='Opening File into ADO stream'
EXEC @HR = sp_OAMethod @objStream, 'LoadFromFile', NULL , @FilePath
IF @HR <> 0 GOTO CLEANUP

SELECT @offset = 73828 --9 * 8192 + 96 + 4

SELECT @strErrorMessage='Setting offset to read file'
EXEC @HR = sp_OASetProperty @objStream, 'Position',  @offset
IF @HR <> 0 GOTO CLEANUP

SELECT @strErrorMessage = 'Reading Version number from mdf'
EXEC @HR = sp_OAMethod @objstream, 'Read', @binary1 OUT , 1
IF @HR <> 0 GOTO CLEANUP

SELECT @strErrorMessage = 'Reading Version number from mdf'
EXEC @HR = sp_OAMethod @objstream, 'Read', @binary2 OUT , 1
IF @HR <> 0 GOTO CLEANUP

SELECT @binary1 + 256 * @binary2 AS DatabaseVersion

END_ROUTINE:
RETURN

CLEANUP:
BEGIN
    EXEC sp_OAGetErrorInfo @objStream,
        @Source OUT,
        @Desc OUT;
        SELECT ErrorInSP='spDBVersion',
        HR = convert(varbinary(4),@HR),
        Source=@Source,
        Description=@Desc,
        Process=@strErrorMessage
    GOTO END_ROUTINE
END
GO

此存储过程需要OLE自动化,因此您希望将其包装在某些重新配置语句中,假设已禁用OLE(因为它可能应该是这样)。

EXEC sp_configure 'show advanced options', 1
RECONFIGURE
GO
EXEC sp_configure 'Ole Automation Procedures', 1
RECONFIGURE
GO

exec spDBVersion 'E:\SQLData\somedatabase.mdf'


GO
EXEC sp_configure 'Ole Automation Procedures', 0
RECONFIGURE
GO
EXEC sp_configure 'show advanced options', 0
RECONFIGURE
GO