Как найти каталог данных для экземпляра SQL Server?
У нас есть несколько огромный базы данных (20 ГБ+), которые в основном содержат статические данные поиска. Поскольку наше приложение выполняет соединения с таблицами в этих базах данных, они должны быть частью каждого локального SQL-сервера разработчиков (т. е. они не могут быть размещены на центральном общем сервере баз данных).
мы планируем скопировать канонический набор фактических файлов базы данных SQL Server (*.MDF и.* ЛДФ) и прикрепить их к локальной базе данных каждого разработчика.
Что лучший способ узнать каталог данных локального экземпляра SQL Server, чтобы мы могли скопировать файлы в нужное место? Это будет сделано с помощью автоматизированного процесса, поэтому я должен быть в состоянии найти и использовать его из сценария сборки.
15 ответов:
это зависит от того, путь по умолчанию для файлов данных и журналов, или нет.
если путь задан явно в
Properties=>Database Settings=>Database default locationsзатем SQL server сохраняет его вSoftware\Microsoft\MSSQLServer\MSSQLServerнаDefaultDataиDefaultLogзначения.однако, если эти параметры не заданы явно, SQL server использует пути данных и журналов базы данных master.
Ниже приведен сценарий, который охватывает оба случая. Это упрощенная версия запроса, который SQL Management Studio работает.
кроме того, обратите внимание, что я использую
xp_instance_regreadвместоxp_regread, так что этот скрипт будет работать для любого экземпляра, по умолчанию или именованным.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 и выше, предполагая, что у вас есть пути по умолчанию (что, вероятно, всегда правильно):
select InstanceDefaultDataPath = serverproperty('InstanceDefaultDataPath'), InstanceDefaultLogPath = serverproperty('InstanceDefaultLogPath')
я наткнулся на это решение в документации для Инструкции Create Database в справке для SQL Server:
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
хотя это очень старый поток, я чувствую, что мне нужно внести свой вклад в простое решение. Каждый раз, когда вы знаете, где в Management Studio находится параметр, к которому вы хотите получить доступ для любого автоматизированного сценария, самый простой способ-запустить быструю трассировку профилировщика в Автономной тестовой системе и захватить то, что Management Studio делает на бэкэнде.
в этом случае, предполагая, что вы заинтересованы в поиске расположения данных и журналов по умолчанию, вы можете сделать следующее:
выберите
SERVERPROPERTY ('instancedefaultdatapath') как [DefaultFile],
SERVERPROPERTY ('instancedefaultlogpath') как [DefaultLog]
для текущей базы данных вы можете просто использовать:
select physical_name fromsys.database_files;чтобы указать другую базу данных, например "модель", используйте sys.master_files
select physical_name from sys.master_files where database_id = DB_ID(N'Model');
начиная с Sql Server 2012, Вы можете использовать следующий запрос:
SELECT SERVERPROPERTY('INSTANCEDEFAULTDATAPATH') as [Default_data_path], SERVERPROPERTY('INSTANCEDEFAULTLOGPATH') as [Default_log_path];(Это было взято из комментария в http://technet.microsoft.com/en-us/library/ms174396.aspx, и проверено.)
различные компоненты SQL Server (данные, журналы, SSAS, SSIS и т. д.) имеют каталог по умолчанию. Настройки для этого можно найти в реестре. Подробнее читайте здесь:
http://technet.microsoft.com/en-us/library/ms143547%28SQL.90%29.aspx
так что если вы создали базу данных, используя только
CREATE DATABASE MyDatabaseNameон будет создан по пути, указанному в одной из настроек выше.теперь, если администратор / установщик изменил путь по умолчанию, то по умолчанию путь к экземпляру хранится в реестре за
HKEY_LOCAL_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_helpdbexec sp_helpdb 'DBName'
все просто:
use master select DB.name, F.physical_name from sys.databases DB join sys.master_files F on DB.database_id=F.database_idэто вернет все базы данных с соответствующими файлами
из графического интерфейса: откройте свойства сервера, перейдите к Параметры Базы Данных и видим расположение базы данных по умолчанию.
обратите внимание, что вы можете удалить файлы базы данных, где вам нравится, хотя это кажется чище, чтобы держать их в каталоге по умолчанию.
вы можете найти расположение данных и журналов по умолчанию для текущего экземпляра SQL Server, используя следующий T-SQL:
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'
маленький придурок: нет папки данных, только по умолчанию папку data.
в любом случае, чтобы найти его, если вы хотите установить для первого экземпляра по умолчанию:
раздел HKEY_LOCAL_MACHINE\программное обеспечение\Майкрософт\SQL-сервера Microsoft\MSSQL данных.1\Setup\SQLDataRoot
Если есть именованный экземпляр, MSSQL.1 становится чем-то вроде MSSQL10.Имя экземпляра.
расширяя ответ" разбрызганные биты", вот полный скрипт, который это делает:
@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
Я бы сделал резервное восстановление просто потому,что его проще и поддержка версий. Справочные данные особенно должны быть версионными, чтобы знать, когда они начали вступать в силу. Прикрепление dettach не даст вам эту способность. Кроме того, с помощью резервных копий вы можете продолжать предоставлять обновленные копии без необходимости завершения работы базы данных.
Алекс - Это верно, но для потомков вот еще один вариант: создать новую пустую базу данных. Если вы используете CREATE DATABASE без указания целевого каталога, который вы получаете... каталоги данных / журналов по умолчанию. Простой.
лично я бы, наверное, тоже:
- восстановить базу данных на ПК разработчика, а не копировать/присоединять (резервные копии могут быть сжаты, выставлены на 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
вы получите расположение по умолчанию, если пользовательская база данных по этому запросу:
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'

Comments