Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/22.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何查找SQL Server实例的数据目录?_Sql_Sql Server_Sql Server 2008_Sql Server 2005_Sql Server 2008 R2 - Fatal编程技术网

如何查找SQL Server实例的数据目录?

如何查找SQL Server实例的数据目录?,sql,sql-server,sql-server-2008,sql-server-2005,sql-server-2008-r2,Sql,Sql Server,Sql Server 2008,Sql Server 2005,Sql Server 2008 R2,我们有一些大型数据库(20GB+),其中大部分包含静态查找数据。因为我们的应用程序对这些数据库中的表执行连接,所以它们必须是每个开发人员本地SQL Server的一部分(即,它们不能托管在中央共享数据库服务器上) 我们计划复制一组规范的实际SQL Server数据库文件(*.mdf和*.ldf),并将它们附加到每个开发人员的本地数据库 找到本地SQL Server实例的数据目录以便将文件复制到正确位置的最佳方法是什么?这将通过自动化过程完成,因此我必须能够从构建脚本中找到并使用它。从GUI:打开

我们有一些大型数据库(20GB+),其中大部分包含静态查找数据。因为我们的应用程序对这些数据库中的表执行连接,所以它们必须是每个开发人员本地SQL Server的一部分(即,它们不能托管在中央共享数据库服务器上)

我们计划复制一组规范的实际SQL Server数据库文件(*.mdf和*.ldf),并将它们附加到每个开发人员的本地数据库


找到本地SQL Server实例的数据目录以便将文件复制到正确位置的最佳方法是什么?这将通过自动化过程完成,因此我必须能够从构建脚本中找到并使用它。

从GUI:打开服务器属性,转到数据库设置,并查看数据库默认位置


请注意,您可以将数据库文件放在任何您喜欢的地方,尽管将它们保存在默认目录中似乎更干净。

对于当前数据库,您可以使用:

要指定另一个数据库,例如“Model”,请使用sys.master\u文件


从sys.master_文件中选择物理_名称,其中database_id=DB_id(N'Model')

小挑剔:没有数据文件夹,只有默认的数据文件夹

无论如何,要找到它,假设您要为第一个默认实例安装:

HKEY\U LOCAL\U MACHINE\SOFTWARE\Microsoft\Microsoft SQL Server\MSSQL.1\Setup\SQLDataRoot


如果有一个命名实例,MSSQL.1就会变成类似MSSQLS10.INSTANCENAME的东西。

我在SQL Server帮助中的Create Database语句文档中偶然发现了这个解决方案:

SELECT SUBSTRING(physical_name, 1, CHARINDEX(N'master.mdf', LOWER(physical_name)) - 1)
                  FROM master.sys.master_files
                  WHERE database_id = 1 AND file_id = 1

SQL Server的各种组件(数据、日志、SSA、SSI等)都有一个默认目录。可在注册表中找到此设置。请在此处阅读更多信息:

因此,如果您仅使用
CREATE database MyDatabaseName
创建数据库,它将在上述设置之一中指定的路径上创建

现在,如果管理员/安装程序更改了默认路径,那么实例的默认路径将存储在

HKEY\U LOCAL\U MACHINE\SOFTWARE\Microsoft\Microsoft SQL Server\[INSTANCENAME]\Setup

如果知道实例的名称,则可以查询注册表。这个示例是特定于SQL 2008的-如果您还需要SQL2005路径,请告诉我

DECLARE @regvalue varchar(100)

EXEC master.dbo.xp_regread @rootkey='HKEY_LOCAL_MACHINE',
        @key='SOFTWARE\Microsoft\Microsoft SQL Server\MSSQL10.MSSQLServer\Setup',
        @value_name='SQLDataRoot',
        @value=@regvalue OUTPUT,
        @output = 'no_output'

SELECT @regvalue as DataAndLogFilePath
当您使用适当的参数发出
CREATE database DBName
语句时,可以在自己的位置覆盖服务器设置来创建每个数据库。您可以通过执行sp_helpdb找到答案

exec sp_helpdb 'DBName'

您可以使用以下T-SQL查找当前SQL Server实例的默认数据和日志位置:

DECLARE @defaultDataLocation nvarchar(4000)
DECLARE @defaultLogLocation nvarchar(4000)

EXEC master.dbo.xp_instance_regread
    N'HKEY_LOCAL_MACHINE',
    N'Software\Microsoft\MSSQLServer\MSSQLServer',
    N'DefaultData', 
    @defaultDataLocation OUTPUT

EXEC master.dbo.xp_instance_regread
    N'HKEY_LOCAL_MACHINE',
    N'Software\Microsoft\MSSQLServer\MSSQLServer',
    N'DefaultLog', 
    @defaultLogLocation OUTPUT

SELECT @defaultDataLocation AS 'Default Data Location',
       @defaultLogLocation AS 'Default Log Location'
展开“飞溅位”回答,下面是一个完整的脚本:

@ECHO off
SETLOCAL ENABLEDELAYEDEXPANSION

SET _baseDirQuery=SELECT SUBSTRING(physical_name, 1, CHARINDEX(N'master.mdf', LOWER(physical_name)) - 1) ^
 FROM master.sys.master_files WHERE database_id = 1 AND file_id = 1;
ECHO.
SQLCMD.EXE -b -E -S localhost -d master -Q "%_baseDirQuery%" -W >data_dir.tmp
IF ERRORLEVEL 1 ECHO Error with automatically determining SQL data directory by querying your server&ECHO using Windows authentication.
CALL :getBaseDir data_dir.tmp _baseDir

IF "%_baseDir:~-1%"=="\" SET "_baseDir=%_baseDir:~0,-1%"
DEL /Q data_dir.tmp
echo DataDir: %_baseDir%

GOTO :END
::---------------------------------------------
:: Functions 
::---------------------------------------------

:simplePrompt 1-question 2-Return-var 3-default-Val
SET input=%~3
IF "%~3" NEQ "" (
  :askAgain
  SET /p "input=%~1 [%~3]:"
  IF "!input!" EQU "" (
    GOTO :askAgain
  ) 
) else (
  SET /p "input=%~1 [null]: "
)   
SET "%~2=%input%"
EXIT /B 0

:getBaseDir fileName var
FOR /F "tokens=*" %%i IN (%~1) DO (
  SET "_line=%%i"
  IF "!_line:~0,2!" == "c:" (
    SET "_baseDir=!_line!"
    EXIT /B 0
  )
)
EXIT /B 1

:END
PAUSE

这取决于是否为数据和日志文件设置了默认路径

如果在
属性
=>
数据库设置
=>
数据库默认位置显式设置了路径
,则SQL server将其存储在
软件\Microsoft\MSSQLServer\MSSQLServer
中的
默认数据
默认日志
值中

但是,如果没有显式设置这些参数,SQLServer将使用主数据库的数据和日志路径

下面是涵盖这两种情况的脚本。这是SQL Management Studio运行的查询的简化版本

另外,请注意,我使用了
xp\u instance\u regrad
而不是
xp\u regrad
,因此此脚本将适用于任何实例,无论是默认实例还是命名实例

declare @DefaultData nvarchar(512)
exec master.dbo.xp_instance_regread N'HKEY_LOCAL_MACHINE', N'Software\Microsoft\MSSQLServer\MSSQLServer', N'DefaultData', @DefaultData output

declare @DefaultLog nvarchar(512)
exec master.dbo.xp_instance_regread N'HKEY_LOCAL_MACHINE', N'Software\Microsoft\MSSQLServer\MSSQLServer', N'DefaultLog', @DefaultLog output

declare @DefaultBackup nvarchar(512)
exec master.dbo.xp_instance_regread N'HKEY_LOCAL_MACHINE', N'Software\Microsoft\MSSQLServer\MSSQLServer', N'BackupDirectory', @DefaultBackup output

declare @MasterData nvarchar(512)
exec master.dbo.xp_instance_regread N'HKEY_LOCAL_MACHINE', N'Software\Microsoft\MSSQLServer\MSSQLServer\Parameters', N'SqlArg0', @MasterData output
select @MasterData=substring(@MasterData, 3, 255)
select @MasterData=substring(@MasterData, 1, len(@MasterData) - charindex('\', reverse(@MasterData)))

declare @MasterLog nvarchar(512)
exec master.dbo.xp_instance_regread N'HKEY_LOCAL_MACHINE', N'Software\Microsoft\MSSQLServer\MSSQLServer\Parameters', N'SqlArg2', @MasterLog output
select @MasterLog=substring(@MasterLog, 3, 255)
select @MasterLog=substring(@MasterLog, 1, len(@MasterLog) - charindex('\', reverse(@MasterLog)))

select 
    isnull(@DefaultData, @MasterData) DefaultData, 
    isnull(@DefaultLog, @MasterLog) DefaultLog,
    isnull(@DefaultBackup, @MasterLog) DefaultBackup
您可以通过使用SMO获得相同的结果。下面是C#示例,但您可以使用任何其他.NET语言或PowerShell

using (var connection = new SqlConnection("Data Source=.;Integrated Security=SSPI"))
{
    var serverConnection = new ServerConnection(connection);
    var server = new Server(serverConnection);
    var defaultDataPath = string.IsNullOrEmpty(server.Settings.DefaultFile) ? server.MasterDBPath : server.Settings.DefaultFile;
    var defaultLogPath = string.IsNullOrEmpty(server.Settings.DefaultLog) ? server.MasterDBLogPath : server.Settings.DefaultLog;
}
在SQL Server 2012及更高版本中,假设您设置了默认路径(这可能永远是正确的做法),它会简单得多:

保持简单:

use master
select DB.name, F.physical_name from sys.databases DB join sys.master_files F on DB.database_id=F.database_id

这将返回所有带有相关文件的数据库

,即使这是一个非常旧的线程,我觉得我需要提供一个简单的解决方案。 任何时候,只要您知道某个参数在Management Studio中的位置,并且希望为任何类型的自动化脚本访问该参数,最简单的方法就是在独立测试系统上运行快速探查器跟踪,并捕获Management Studio在后端的操作

在本例中,假设您对查找默认数据和日志位置感兴趣,可以执行以下操作:

选择
SERVERPROPERTY('instancedefaultdatapath')为[DefaultFile],

SERVERPROPERTY('instancedefaultlogpath')作为[DefaultLog]

如果用户数据库通过此查询:

declare @DataFileName nVarchar(500)

declare @LogFileName   nVarchar(500)


set @DataFileName = (select top 1 RTRIM(LTRIM(name)) FROM master.sys.master_files where database_id >4 AND file_id = 1)+'.mdf'
set @LogFileName =   (select top 1 RTRIM(LTRIM(name)) FROM master.sys.master_files where database_id >4 AND file_id = 2)+'.ldf'

select  
( SELECT top 1 SUBSTRING(physical_name, 1, CHARINDEX(@DataFileName, LOWER(physical_name)) - 1) 
FROM master.sys.master_files
WHERE database_id >4 AND file_id = 1) as 'Data File'
,

(SELECT top 1 SUBSTRING(physical_name, 1, CHARINDEX(@LogFileName, LOWER(physical_name)) - 1)
FROM master.sys.master_files
WHERE database_id >4 AND file_id = 2)  as 'Log File'

自Sql Server 2012起,您可以使用以下查询:

SELECT SERVERPROPERTY('INSTANCEDEFAULTDATAPATH') as [Default_data_path], SERVERPROPERTY('INSTANCEDEFAULTLOGPATH') as [Default_log_path];

(这是从上的一条评论中摘取的,并经过了测试。)

我会做一次备份还原,因为它更简单,而且支持版本控制。参考数据尤其需要进行版本控制,以了解其何时开始生效。DettachAttach不会给你这种能力。此外,通过备份,您可以继续提供更新的副本,而无需关闭数据库

是正确的选择,但对于后代来说,还有另一个选择:创建一个新的空数据库。如果使用CREATEDATABASE而不指定目标目录,则会得到。。。默认的数据/日志目录。简单

但就我个人而言,我可能会:

  • 将数据库恢复到开发人员的PC上,而不是复制/附加(备份可以压缩,在UNC上公开),或
  • 首先,使用链接服务器避免这样做(取决于有多少数据通过连接)
ps:20gb不是很大,即使在2015年也是如此。但这都是相对的

SELECT DISTINCT dbo.GetDirectoryPath(filename) AS InstanceDataPaths
FROM sys.sysaltfiles WHERE filename like '%.mdf' and filename not like '%\MSSQL\Binn\%'

SELECT DISTINCT dbo.GetDirectoryPath(filename) AS InstanceLogPaths
FROM sys.sysaltfiles WHERE filename like '%.ldf' and filename not like '%\MSSQL\Binn\%'


您可以从

下载详细的SQL脚本。这要求我知道SQL Server实例名称(例如,MSSQL.1、MSSQL.2、MSSQL.\N\u)。如何获取该实例名称?对于默认实例,它不是名称,而是数字。将哪个实例添加到ins
SELECT DISTINCT dbo.GetDirectoryPath(filename) AS InstanceDataPaths
FROM sys.sysaltfiles WHERE filename like '%.mdf' and filename not like '%\MSSQL\Binn\%'

SELECT DISTINCT dbo.GetDirectoryPath(filename) AS InstanceLogPaths
FROM sys.sysaltfiles WHERE filename like '%.ldf' and filename not like '%\MSSQL\Binn\%'