Sql SMO: Как получить путь к физическому имени файла базы данных? - PullRequest
5 голосов
/ 23 января 2009

Я пытаюсь вернуть физический путь к файлу базы данных mdf / ldf.

Я пытался использовать следующий код:

Server srv = new Server(connection);
Database database = new Database(srv, dbName);

string filePath = database.PrimaryFilePath;

Однако это вызывает исключение. «Database.PrimaryFilePath» вызвало исключение типа «Microsoft.SqlServer.Management.Smo.PropertyNotSetException», даже если база данных, с которой я работаю, существует, а ее файл mdf находится c: \ Program Files \ Microsoft SQL Server \ MSSQL.1 \ MSSQL

Что я делаю не так?

Ответы [ 5 ]

5 голосов
/ 24 января 2009

Обычно проблема в том, что свойство DefaultFile имеет значение null. Файл данных по умолчанию - это место, где файлы данных хранятся на экземпляре SQL Server, если иное не указано в свойстве FileName. Если не указано другое местоположение по умолчанию, свойство вернет пустую строку.

Итак, это свойство ничего не возвращает (пустая строка), если вы не установили местоположение по умолчанию.

Обходной путь - проверить свойство DefaultFile. Если он возвращает пустую строку, используйте SMO для получения основной базы данных, а затем используйте свойство Database.PrimaryFilePath для получения местоположения файла данных по умолчанию (поскольку оно не изменилось)

Поскольку вы говорите, что проблема связана с вашим PrimaryFilePath:

  • Подтвердите, что ваше соединение открыто
  • Подтвердите, что доступны другие свойства
2 голосов
/ 16 июня 2009

Вот как я это делаю, подготовленный для нескольких имен файлов. Откройте файл database.LogFiles, чтобы получить тот же список имен файлов журнала:

private static IList<string> _GetAttachedFileNames(Database database)
{
    var fileNames = new List<string>();

    foreach (FileGroup group in database.FileGroups)
        foreach (DataFile file in group.Files)
            fileNames.Add(file.FileName);

    return fileNames;
}
0 голосов
/ 27 февраля 2016
using Smo = Microsoft.SqlServer.Management.Smo;

public string GetDataBasePath(string strDatabaseName)
{
    ServerConnection srvConn = new ServerConnection();
    srvConn.ConnectionString = "<your connection string goes here>";
    Server srv = new Server(srvConn);

    foreach (Smo.Database db in srv.Databases)
    {
        if (string.Compare(strDatabaseName, db.Name, true) == 0)
        {
            return db.PrimaryFilePath;
        }
    }

    return string.Empty;
}
0 голосов
/ 22 января 2015

Я думаю, что самый простой подход - запустить скрипт SQL на экземпляре сервера SQL, который всегда будет возвращать вам правильные данные и пути к файлам журналов. Следующий sql сделает трюк


SELECT
    db.name AS DBName,
    (select mf.Physical_Name FROM sys.master_files mf where mf.type_desc = 'ROWS' and db.database_id = mf.database_id ) as DataFile,
    (select mf.Physical_Name FROM sys.master_files mf where mf.type_desc = 'LOG' and db.database_id = mf.database_id ) as LogFile
FROM sys.databases db
order by DBName

Вы все еще можете выполнить этот sql, используя SMO, если хотите, который вернет вам набор данных, а затем вы сможете извлечь эту информацию.


var result = new List();
            var server = new Server( serverInstanceName );
            var data = server.Databases[ "master" ].ExecuteWithResults(sql);

            foreach ( DataRow row in data.Tables[ 0 ].Rows )
                result.Add( new DatabaseInfo( row[ "DBName" ].ToString(), row[ "DataFile" ].ToString(), row[ "LogFile" ].ToString() ) );

            return result;

Если вы будете использовать этот фрагмент, то обязательно создайте класс DatabaseInfo, в котором будет храниться информация, возвращаемая экземпляром сервера Sql.

0 голосов
/ 09 апреля 2009

Сервер srv = новый Сервер (соединение); DatabaseCollection dbc = svr.Databases; База данных базы данных = dbc ["dbName"]; строка filePath = database.PrimaryFilePath;

...