Window authentication in sql server and asp.net - c#

I am using Window Authentication for sql database for my asp.net web application.but after i deploy my website to another computer I'm unable to connect to the database.Is there any property for window authentication to set user name and password in web.config file.

Does this sound like your scenario?
IIS web app built on local machine
Web app uses windows authentication
Web app talks to database also on local machine
Web app users also have valid database logins
Web app users credentials are passed to database via trusted connection
Everything works great. Then you move it to a different environment where the database and IIS are no longer on the same server and then you cannot get the database to recognize the credentials IIS is passing in?
If so, then welcome to my hell a few months ago. The problem is that once the two processes are not on the same box, they don't trust each other any more. Network administration permissions are required to get the two process to trust each other across server boundaries. Unfortunately, I didn't blog about it but the general steps were
mark the IIS service account as trustworthy (Active directory setting)
set the service principal name (SPN) to either the netbios name or FQDN
something had to be set on both boxes to indicate they could trust each other
Sorry for the vague recollection and as I wasn't the one with credentials to fix anything, I only got to observe them clicking the buttons. The starting article on How to connect to SQL Server using Windows Authentication got us fairly far down the track.

This deals with the fact that on your developer box, you (or the anon user? or the user the develper web service spins up as?) is trusted by the local instance of SQL. But, when you deploy, the user ASP.NET runs under is not trusted.
Options
As George mentioned, go with a SQL logon, not windows
Set up a proper trust between the web server and SQL Server
Impersonate a user for the data context (this can get complex, btw)

You are most likely using a trusted connection string, e.g.
Data Source=myServerAddress;Initial
Catalog=myDataBase;Integrated
Security=SSPI;
...as you are using windows authentication. You need to use a standard connection string. e.g.
SQL Server 2008:
Data Source=myServerAddress;Initial
Catalog=myDataBase;User
Id=myUsername;Password=myPassword;
Just be sure to set up a non-windows authentication user within SQL Server.

Authentication mode should be set in the web.config. Also, check if anonymous authentication is disabled or not.
<authentication mode="Windows"/>

Related

SQL Connection Using Domain Username And Password

I have developed an ASP.Net website. The problem I am facing is when I run the application in IIS on my system using the connection string in web.config ("Data Source=.\;Initial Catalog=ITS;Integrated Security=True") it works well. I connects to the database and displays the data.
I have installed the database on a domain computer with the ASP.NET package in IIS. The problem here is it doesn't connects to the database. I have tried to use the connection string like this "Data Source=.\;Initial Catalog=ITS;UID=S1\ISLWW74562S;PWD=delta$%67;Integrated Security=True"
Where S1 is the domain name and ISLWW74562S is the username.
It gives an error cannot find the login S1\ISLWW74562S$
Can anyone help me how and what is the proper way to use the connection string on a domain computer.
Thanks
Remove the UID=S1\ISLWW74562S;PWD=delta$%67 from the connection string, and instead in IIS, create a special application pool for your web site and configure such application pool to run under the domain account.
Take a look at this to see how to setup the application pool to use a custom account.
Also, make sure that the domain account that you are using has the required access to the SQL database that you want to use.
If you are using Microsoft SQL server, then you need to use SQL management studio to create a new login for the domain user and give it the appropriate access to the database that you are using.
When you use Integrated Security, you don't get to specify the username and password. Sql Server will not allow you to do this. Instead, it's looking for a token that was issued by the domain controller, and that's all it will accept.
You can get a token like this for your application by using the Impersonation feature in IIS or by setting up the application pool for IIS to run as that user account.

'Domain/MachineName$' being used for authentication instead of 'Domain/UserName'

The following post may look same but I was unable to correct the problem after attempting all the solutions provided as answers.
(Login failed for user 'DOMAIN\MACHINENAME$')
MY PROBLEM
I am deploying a asp.net web-app with forms authentication enabled on my IIS7 dev server in a Windows Network. My SQL Server is deployed on a remote box, in the same network, with necessary TCP ports opened for remote connections. All the domain users have been given access to necessary databases in SQL server.
Now when I try to run my web-app, following error comes up:
Login failed for user 'DOMAIN\MachineName$'.
I have already given adequate permissions to NT AUTHORITY\NETWORK SERVICE in my SQL server.
I don't want to give any permission to 'DOMAIN\MachineName$' in the SQL server as the developers keep changing the machine names for various test purposes.
The connecting string I am using is:
"Server=SQL-SERVER;Initial Catalog=MyDatabase;Integrated Security=SSPI;Persist Security Info=False"
SQL Provider is System.Data.SqlClient
Anonymous and Form authentication are enabled as my web-app contains login.aspx.
The point is that whenever you use NT AUTHORITY\NETWORK SERVICE as your application pool user, the system translates this in the network to DOMAIN\MachineName$.
What we do is to use the user name of the developer to connect to the machine by setting the username of the application pool to the developer's name.
I also encounter same problem in my intranet environment. The solution is simple yet hard to grab the idea. Usually, The IT Security In-charge will give you active directory service account to log in to your database. You can manage to log in with ssms but it fails in IIS because IIS choose to connect with domain/computername. So set custom account and fill in your domain/username and password.
In IIS Manager, select the application pool that your web app uses or
create a new one if you use the default one.
Click on “Advanced Settings” in the right Actions bar. Under Process Model, click on
the “Identity” value and select “Custom account”.
Click on the “Edit” and enter domain/user name and password for user account.
If you enter all information correctly, the pop-up will be closed successfully
without any error messages.
After that stop your Web Site.
Back again to your application pool and click on the “Recycle”.
Start your Web Site.
And that's it. you web application will successfully connect from IIS.

Impersonating IIS DefaultAppPool in standalone application

Description of my problem sounds somewhat complicated, what makes me think that my approach is flawed, so I will also appreciate any better idea.
Short description:
Given connection string to MSSQL 2008 DB and website name deployed on IIS6, I want to verify programatically whether website is able to connect to database.
Long description:
I have MSSQL Server database, let's call it portal_db.
I have an application deployed on IIS6, called portal. I can access it by url http://localhost/portal . In Web.config file I specified connection string to my database, which look like: "server=(local)\SQLEXPRESS;trusted_connection=yes;database=portal_db"
Web application is accessing database using System.Data.SqlClient.SqlConnection, without any wrappers, ORMs, mappings, anything.
Website is configured to run in appool PortalAppPool. It's using ApplicationPoolIdentity as a security context.
It is not possible to easily modify web application code (particularly the way it accesses database)
When my web application tries to connect to database it either succeeds or fails, depending on whether user IIS APPPOOL\PortalAppPool is configured in MSSQL database. That's a part which I understand, but when deploying my app I often forget to create new user/login in db for apppool virtual account. So what I want to do, is to verify from separate, standalone, console app (preferably written in C#, but not necessarily), whether my web application can access database, in following way:
Read connection string from Web.config
Read app pool identity settings (managed to do this by Directory Services API)
Impersonate identity with credentials defined on app pool (using impersonation class I found here: http://platinumdogs.me/2008/10/30/net-c-impersonation-with-network-credentials/ which uses ideas found in many other places, including MSDN)
Open SqlConnection with connection string read from Web.config
It boils down to following snippet:
using (new Impersonator("IIS APPPOOL\\PortalAppPool", "", ""))
{
SqlConnection conn = new SqlConnection(databaseConnectString);
conn.Open();
}
Everything works very well, when my app pool security context is set to any other value than AppPoolIdentity - specific user, local system, etc. When I change credentials passed to Impersonator to my user's name and password, I get desired result (exception when I have no login mapping in database, and everything is OK when I add one). But I just seem to not be able to impersonate IIS APPPOOLS\PortalAppPool virtual account - just have no idea what parameters should be passed to LogonUser - I would not be surprised if it would not be even possible. Maybe I am focused on impersonation approach too much (I am using it to access registry keys and services of other users and it works good), and maybe there is some better way.
If you have any other, better ideas, or need some more explanation to this problem, please let me know.
I don't think you can impersonate a virtual account (IIS service account). They are special service accounts setup mainly for IIS security. They are for local services only and cannot be attached to any domains. Virtual accounts in Windows Server 2008 R2 and Windows 7 are "managed local accounts" that provide the following features to simplify service administration:
No password management is required.
The ability to access the network with a computer identity in a domain environment.
You cannot "Log into" a virtual account, they are used by windows for security purposes:
Some light reading if you have time:
This gives a brief overview of MSAs and Virtual Accounts
The differences between MSAs and Virtual Accounts
The dirty details on each and how to manage them
To solve your original problem, you could build an app that could do the same logic but check the sql server if it has the correct users setup instead of simply trying to login with the account.

Login failed for user 'IIS APPPOOL\ASP.NET v4.0'

I have a web project (C# Asp.Net, EF 4, MS SQL 2008 and IIS 7) and I need to migrate it to IIS 7 locally (at the moment works fine with CASSINI).
Locally in IIS I have my Default Web Site with my deploy. Both my deploy and Default Web Site are on pool ASP.NET v4.0 (look image for settings) the pool target Framework 4 as my web project.
When visiting the site, the browser does not show the page and allow the browser to download the page instead.
I have other projects running on IIS locally and they work with no problems (but they do not use Entity Framework).
Using the Event Logger I see errors as below:
Exception information:
Exception type: EntityException
Exception message: The underlying provider failed on Open.
at System.Data.EntityClient.EntityConnection.OpenStoreConnectionIf(Boolean openCondition, DbConnection storeConnectionToOpen, DbConnection originalConnection, String exceptionCode, String attemptedOperation, Boolean& closeStoreConnectionOnFailure)
Login failed for user 'IIS APPPOOL\ASP.NET v4.0'.
at System.Data.ProviderBase.DbConnectionPool.GetConnection(DbConnection owningObject)
at System.Data.ProviderBase.DbConnectionFactory.GetConnection(DbConnection owningConnection)
at System.Data.ProviderBase.DbConnectionClosed.OpenConnection(DbConnection outerConnection, DbConnectionFactory connectionFactory)
at System.Data.SqlClient.SqlConnection.Open()
at System.Data.EntityClient.EntityConnection.OpenStoreConnectionIf(Boolean openCondition, DbConnection storeConnectionToOpen, DbConnection originalConnection, String exceptionCode, String attemptedOperation, Boolean& closeStoreConnectionOnFailure)
Related question
UPDATE:
You can read in the resources on this question that permissions must be granted on MS SQL 2008 manually as arift explain in his answer.
Using IIS 7.5 and MS SQL 2008 R2, setting manually permission should not be necessary.
Looks like it's failing trying to open a connection to SQL Server.
You need to add a login to SQL Server for IIS APPPOOL\ASP.NET v4.0 and grant permissions to the database.
In SSMS, under the server, expand Security, then right click Logins and select "New Login...".
In the New Login dialog, enter the app pool as the login name and click "OK".
You can then right click the login for the app pool, select Properties and select "User Mapping". Check the appropriate database, and the appropriate roles. I think you could just select db_datareader and db_datawriter, but I think you would still need to grant permissions to execute stored procedures if you do that through EF. You can check the details for the roles here.
You can change the ApplicationPoolIdentity from IIS7 -> Application Pools -> Advanced Settings.
Under ApplicationPoolIdentity you will find local system. This will make your application run under NT AUTHORITY\SYSTEM, which is an existing login for the database by default.
Edit: Before applying this suggestion you should note and understand the security implications.
I solved this problem using sql as following image.
Right click on db-> properties -> permission -> View Server permission -> and then select IIS APPPOOL\ASP.NET v4.0 and grant permission.
ensure you have...
Trusted_Connection=false;
in your connection String
Run this sql script
IF NOT EXISTS (SELECT name FROM sys.server_principals WHERE name = 'IIS APPPOOL\DefaultAppPool')
BEGIN
CREATE LOGIN [IIS APPPOOL\DefaultAppPool]
FROM WINDOWS WITH DEFAULT_DATABASE=[master],
DEFAULT_LANGUAGE=[us_english]
END
GO
CREATE USER [WebDatabaseUser]
FOR LOGIN [IIS APPPOOL\DefaultAppPool]
GO
EXEC sp_addrolemember 'db_owner', 'WebDatabaseUser'
GO
If in the connection string you have specified:
User ID=xxx;Password=yyy
but in the connection string there is:
Trusted_Connection=true;
SQL Server will use Windows Authentication, so your connection values will be ignored and overridden (IIS will use the Windows account specified in Identity user profile).
more info here
The same applies if in the connection string there is:
Integrated Security = true;
or
Integrated Security = SSPI;
because Windows Authentication will be used to connect to the database server.
more info here
go to iis -> application pools -> find your application pool used in application
select your application pool used for the application right click select advanced settings
Select application pool identity
select built in as Local System
and click ok
I had to create a user `IIS APPPOOL\DefaultAppPool' as shown below in SQL Server. Security > Login > Right click and press 'New Login'. You only enter the username as show in red in the screen.
Then go into that new user properties, check the database this user will access (marked in blue below) and select db_owner as well. I had to select because although connection was working but subsequent SELECT queries didn't had the access if this was not selected.
These two should do it. Basically you are making the new user owner for the database so it has full access.
You don't need to restart SQL Server or anything, should work.
1_in SqlServer Security=>Login=>NT AUTHORITY\SYSTEM=>RightClick=>Property=>UserMaping=>Select YourDatabse=>Public&&Owner Select=>OK
2_In IIs Application Pools DefaultAppPool=>Advance Setting=>Identity=>LocalSystem=>Ok
I hate the ApplicationPoolIdentity. I always set a Windows User Account as the account on AppPools.
As adrift says, it does sound like a database security issue. So create an NT user account, assign it to the ASP.NET v4.0 AppPool and then grant it permission on the website folder and to the relevant table(s) in SQL.
First thing you need to clear if you are using windows authentication and you are not mentioning any username password in your connection string then:
What happens when you run your code through localhost: when you run your wcf test client from localhost, it will be able to communicate to database as local debug mode application is calling database by your account's service. So it has access to database because devenv.exe is running under your user account.
But when you deploy your web service in IIS. Now understand this service runs under IIS not under your account. So you need to assign access rights to IIS service to access the sql server for windows authentication. Here your web service would not be able to communicate to the SQL server because of access rights issue and Login Failed for user_______ (here your user will come)
So if you are using windows authentication to connect your database, you just have to change the IIS Application pool settings. You need to change IIS Application pool's identity to local System.
Below are the Steps for windows authentication WCF:
1) Open IIS (windows+R (run) then type inetmgr, then click ok)
2) double click your PC name under Connections
3) Click Application Pools
4) Select your app pool (DefaultAppPool)
5) Then under actions on the right click Advanced Settings:
6) Go to Process Model section and
7) click on Identity.
8) Now select LocalSystem.
Now open your sql server management studio:
open run-> then type ssms ->then press ok
In ssms, login using your windows authentication account.
Open security tab expand logins tab then you will be able to view your account.
Now open properties of your account
go to userMapping then select the database you want to connect
then check the role membership services you want to use for the selected database. click ok.
(For network services i.e. intranet users you need to configure above settings for NT AUTHORITY\SYSTEM user too)
add Trusted_Connection=True; property in your connection string. Save it & deploy the web service. Restart app pool.
you will be able to connect the database now.
Don't use Integrated Security.
Use User Id=yourUser; pwd=yourPwd;
This solves the problem.
I had this issue and it was actually caused by something different - I had the 'IIS APPPOOL\ASP.NET v4.0' user in my database but it still wasn't working.
I had recently upgraded my SQL Server Install and in the process the User had become disconnected from the Login - so there was an 'IIS APPPOOL\ASP.NET v4.0' under Database -> Security -> Users BUT no User not under Security -> Logins.
Added the Login 'IIS APPPOOL\ASP.NET v4.0' to Security -> Logins, SQL Server automatically mapped it to the User in the database (this used to have to be done manually) and problem fixed.
I had this message and I use Windows Authentication on the web server.
I wanted the currently authenticated web user to be authenticated against the database, rather than using the IIS APPPOOL\ASP.NET v4 User specified in the App Pool.
I found by entering the following in the web.config fixed this for me:
<system.web>
<identity impersonate="true" />
</system.web>
https://msdn.microsoft.com/en-us/library/bsz5788z.aspx
I see other Answers regarding creating the AppPool username in the SQL DB or just to use SQL Auth. Both would be correct if you didn't want to capture or secure individual Windows users inside SQL.
Tom
I Have the same problem I solved it by changing Integrated Security=True to false
now its working
Setting the identity only makes this work in my pages.
Cassini runs your website as your own user identity when you start up the Visual Studio application. IIS runs your website as an App Pool Identity. Unless the App Pool Identity is granted access to the Database, you get errors.
IIS introduced App Pool Identity to improve security. You can run websites under the default App Pool Identity, or Create a new App Pool with its own name, or Create a new App Pool with its own name that runs under a User Account (usually Domain Account).
In networked situations (that are not in Azure) you can make a new App Pool run under an Active Directory Domain user account; I prefer this over the machine account. Doing so gives granular security and granular access to network resources, including databases. Each website runs on a different App Pool (and each of those runs under its own Domain User account).
Continue to use Windows Integrated Security in all Connection Strings. In SQL Server, add the Domain users as logins and grant permissions to databases, tables, SP etc. on a per website basis. E.g. DB1 used by Website1 has a login for User1 because Website1 runs on an App Pool as User1.
One challenge with deploying from the Visual Studio built-in DB (e.g. LocalDB) and built-in Web Server to a production environment derives from the fact that the developer's user SID and its ACLs are not to be used in a secure production environment. Microsoft provides tools for deployment. But pity the poor developer who is accustomed to everything just working out of the box in the new easy VS IDE with localDB and localWebServer, because these tools will be hard to use for that developer, especially for such a developer lacking SysAdmin and DBAdmin support or their specialized knowledge. Nonetheless deploying to Azure is easier than the enterprise network situation mentioned above.
If you have your connection string added in your web.config, make sure that "Integrated Security=false;" so it would use the id and password specified in the web.config.
<connectionStrings>
<add providerName="System.Data.SqlClient" name="MyDbContext" connectionString="Data Source=localhost,1433;Initial Catalog=MyDatabase;user id=MyUserName;Password=MyPassword;Trusted_Connection=true;Integrated Security=false;" />
</connectionStrings>
As pointed out, Do not use Windows Authentication, Use SQL Server Authentication
Also if you created connection using "Server Connection" dialog, make sure to check the connections in web.config. It is likely that you created/modified connection and it was stored as trusted connection in web.config. Simply use this authentication
<add name="MyDBConnectionString" connectionString="Data Source=localhost;Initial Catalog=Finantial;User ID=xxx;Password=xxx" providerName="System.Data.SqlClient"/>
which should fix the error.
Another way of granting permission to the database for the user IIS APPPOOL\ASP.NET v4.0 is as follows.
Add New User with User Name and Login name as IIS APPPOOL\ASP.NET
v4.0 with your default schema.
Go to Owner schema and Membership, Check db_datareader, db_datawriter
You can face this wrong in specific database which is created after SSMS update. Open SSMS and select your databases and open your required database then click Security--> Users--> and right click on Users and click again on 'New User' and add 'NT AUTHORITY\Authenticated Users' and save you work and go to your Form on Web/Desktop whatever do you. Enjoy....
Thought I'd post this as an answer as it is relevant to the question and can answer it in some cases.
That same message appears also if the database does not exist!
Be sure your connection string has no misspellings, is pointing to the right server instance, etc.
In Asp.net webform,
this error fixed when installing asp.net from:
Server Manager > Manage > Add Role and Feature > Server Roles > Web Server (IIS) > Web Server > Application Development > ASP.NET 3.5/4.6 is installed.
my problem fixed.
something similar happened to me what worked for me was changing the property Integrated Security = True to Integrated Security = false in the web.config of the website
go to iis -> application pools -> find your application pool used in application -> click it and then click 'Advance Settings' in Actions panel. Find 'Identity' property and change it to localsystem.
I ran into this error with IIS and dotnet core.
A quick work around for anyone who are using Sql authentication, have your appsetting.json read this to disable Windows Authentication and use SQL authentication.
(This is in the appsetting.json(default one) or anywhere you have specified your db connection string)
"dbContext": "data source=servername;initial catalog=dbname;user id=your_server_username;password=your_server_password;trusted_connection=false;multipleactiveresultsets=true",
cheers and happy coding
Have you done what #Teddy recommended and you STILL get the same error?
Make sure you're changing the settings for the app pool that corresponds to your virtual directory and not the parent server. Each virtual directory has its own AppPool and doesn't inherit.
In DefaultAppPool set NetworkService in the Identity property and in Sql Server add User Network Service and give it the appropiate permissions to your database, that's work very well for me, I've tested locally but I think this is the best configuration for connecting from any other computer in the network. when you set LocalSystem in the Identity in IIS that's work well and it is not necessary to create any other user in Sql Server but I think that will not work in a network environment.
I ran into the same problem testing ASP.NET Web API
Developed Web.Host in Visual Studio 2013 Express
Database created in SQL Server 2012 Express
Executed test using built in IIS Express (working)
Modified to use IIS Local (from properties page - web option)
Ran test with Fiddler
Received error - unable to open database for provider....
citing 'APPPOOL\DefaultAppPool'
Solution that worked.
In IIS
Click on application pool 'DefaultAppPool'
Set Identify = 'ApplicationPoolIdentity'
Set .NET framework = v4.0 (even though my app was 4.5)
In SQL Server Management Studio
Right click on Security folder (under the SQL Server engine so applies to all tables)
Right click on User and add 'IIS APPPOOL\DefaultAppPool'
In securables on the 'Grant' column check the options you want to give.
Regarding the above if you are a DBA you probably know and want to control
what those options are. If you are like me a developer just wanted to test
your WEB API service which happens to also access SQL Server through EF 6
in MVC style then just check off everything. :) Yes I know but it worked.
In case you add a new login, make sure that under server properties ( rightclick -> properties)/security, authentication mode is set to both sqlserver and windows not only windows.

SQLNET.AUTHENTICATION_SERVICES= (NTS) and ASP.NET

I'm trying to access an oracle database using
using System.Data.OracleClient;
from a console application, accessing the database is fine. however from an ASP.NET web site i get the error:
ORA-12640: Authentication adapter initialization failed
I've googled around and found that changing sqlnet.ora file would solve the issue
//before
SQLNET.AUTHENTICATION_SERVICES= (NTS)
//after
SQLNET.AUTHENTICATION_SERVICES= (NONE)
Later I found another application on the same server, that uses other database of Oracle as well, is requiring the value of SQLNET.AUTHENTICATION_SERVICES to be "NTS". This would cause my web site to fail accessing the database with the error ORA-12640. I have tried "ALL" as value but still it didn't work.
How can I configure my website to access the oracle database while sqlnet.ora is configured as "SQLNET.AUTHENTICATION_SERVICES= (NTS)" ?
P.S. the website uses Windows Authentication and impersonate as follow:
<authentication mode="Windows"/>
<identity impersonate="true"/>
This looks like the multi-hop impersonation issue to me.
If it's an option for you, I suggest having your application run under a single identity when accessing the database (this should also allow connection pooling to occur as a beneficial side-effect).
To do this, you would need to configure an app pool to run under an account that has access to Oracle. Once the application is running under that app pool, turn impersonation off in your application so that the database calls occur using the app pool identity.
If you have to impersonate the calling users over the network, the method used will depend on your environment. For more information, see How to Use Impersonation and Delegation in ASP.NET 2.0.
I was also facing the same issue, but finally got it working. Created a service account(named kerb_user in the active directory) and changed the app pool authentication to run as "kerb_user".
First I tried with this, but it was failed.
Please check the request log in oracle database, where you can verify the OS_USERNAME carefully. In my case it shows kerb_user, where as for other kerberos user requested OS_USERNAME was suffixed with domain name, which was missing in my case.
Then I did two changes.
Modified the app pool identity with domain name: kerb_user#xyz.com
Modified the sqlnet.ora file on app server and changed authentication to "ALL"
//before - not working
SQLNET.AUTHENTICATION_SERVICES= (NONE)
//after - worked
SQLNET.AUTHENTICATION_SERVICES= (ALL)
Debugging
Check the oracle log, if requested OS_USERNAME is suffixed with domain name(here kerb_user#xyz.com) or not. If suffixed, will work for sure.
Please verify service user on both side(app- AD User and db- Service User) server, user should have same name.
Verify the service user access at db server and ensure, user must have kerberos access to that database.
Check the SPN settings
Ref: https://www.codeproject.com/Articles/27554/Authentication-in-web-services-using-C-and-Kerbero

Categories