0

I connect to the database in asp.net mvc 3 project. Also I have a windows service project in my solution which on some event writes the data into this database.

The difficulty is that when the code from windows service project needs to connect to the database I get SqlException:

Cannot open database "WebStore" requested by the login. The login failed. Login failed for user 'NT AUTHORITY\SYSTEM'.

Here is the code from windows service:

    public static string GetConnectionString()
    {
        return @"Data Source=(LocalDB)\v11.0; DataBase=WebStore; 
                AttachDbFilename=myDbFullPath;
                Integrated Security=True;Connect Timeout=30";
    }

And in the event handler that writes to the database:

using (var conn = new SqlConnection(GetConnectionString()))
{
    conn.Open();
    var productId = Convert.ToInt32(Regex.Match(e.Name, @"\d+").Value);
    const string cmd1 = "UPDATE Products SET ImageModifiedDate=@date WHERE ProductId=@productId";

    using (var command = new SqlCommand(cmd1, conn))
    {
        command.Parameters.AddWithValue("@productId", productId);
        command.Parameters.AddWithValue("@date", DateTime.Now);
        command.ExecuteNonQuery();
    }
 }

The exception occurs in conn.Open(); line. If I comment this line new exception will occur in command.ExecuteNonQuery();:

InvalidOperationException: Opened and available connection is needed for ExecuteNonQuery. Connection is closed.

Question: How to open a connection to the SQL Server database that is already attached in another project?

Edit 1: I use the following code to create new login and new user in my DB:

CREATE LOGIN user1
WITH PASSWORD = 'password1';
GO
CREATE USER user1 FOR LOGIN user1;
GO

Than I'm trying to attach my DB in Server Explorer: I choose "Use Sql Server Autherntication" and enter user name: user1, password: password1.

And I get:

The attempt to attach to the database failed with the following information:
Login failed for user 'user1'.

Edit 2: I set this properties:

processInstaller.Username = "user1";
processInstaller.Password = "password1";

and than run in cmd:

installutil /name=user1 /password=password1 MyService.exe

and I get System.ComponentModel.Win32.Exception:
the comparison between user names and security identifiers haven't been executed.

What do I do wrong?

Edit 3: I set my username and password in services.msc and processInstaller "Account" property I left with "Local System". It runs but when I change the image (and the event handler trying to access my database) I get:

Cannot attach file 'C:\Users\Aleksey\repos\working-copy\WebStore\WebStore\App_Data\WebStore.mdf' as database 'WebStore' because this file is already in use for database 'C:\USERS\ALEKSEY\REPOS\WORKING-COPY\WEBSTORE\WEBSTORE\APP_DATA\WEBSTORE.MDF',

In the connection string I added credentials of user which I've created in the database:

User Id=user1;PASSWORD=password1;

Besides, when I'm trying to add connection in server explorer and use Sql Server Authentication and I enter user1 and password1 I get the message from Edit 1.

Should I use in server explorer *Windows Authentication* and in windows service in the connection string: User Id=user1;PASSWORD=password1; ?

4

1 回答 1

1
Cannot open database "WebStore" requested by the login. The login failed. Login failed for user 'NT AUTHORITY\SYSTEM'.

发生这种情况是因为您的服务使用 LocalSystem 帐户运行,并且您正在使用集成安全性连接到 SQL 服务器,而 SYSTEM 不应该在那里访问。所以三选一:

  1. 切换到 SQL Server 身份验证。这包括在数据库中创建登录名和修改连接字符串
  2. 使用具有它真正需要的唯一权限的特定用户运行服务(这实际上是一个好主意),并授予该用户对数据库的访问权限,以便它可以连接到集成安全性。这是最简单的,因为它不需要对代码进行任何更改
  3. 如果您确实需要以 SYSTEM 身份运行,则可以使用模拟通过 LogonUser 切换到另一个用户(如选项 2 中的用户)。这样一来,您最终只能使用选项 2 来访问数据库,并为其余的服务代码保留 SYSTEM 权限。

第二个错误

InvalidOperationException: Opened and available connection is needed for ExecuteNonQuery. Connection is closed.

是由第一个错误引起的,无法打开连接会导致此问题。如果没有打开的连接,您将无法执行任何操作,ADO.Net 可以确保这一点。

所以第一个错误是唯一重要的错误。

我建议您使用选项二,因为这是安全实践方面的最佳选择,并且由于您在集成安全中运行,因此您不必存储任何密码,当您的应用程序在多个不同的环境中时,这是一个加分项数据库,用户,密码和你有什么。每个环境,权限和您设置的只是一个用户。

于 2013-02-27T13:18:09.163 回答