I have as ASP.Net 2.0 website with SQL Server as database and C# 2005 as the programming language. The website is almost complete and all the links are working fine. But I want to prevent normal users from opening a couple of pages. When any user clicks on those specific links, another page opens which contains a ASP Login control. The user has to supply a valid userid and password to display the links pointing to the restrictive pages. But being a newbie, I don't know how to leverage the full power of the ASP Login control. Because, if a user gets to know the exact url of the restricted pages, then he/she can bypass the login control and directly access those pages by typing the url into the address bar. I want to prevent this. If the user types the url directly in the address bar, I want that the page itself should check, whether the user has been validated through the Login control and either display the page or point the user to the Login page.
How do I implement this feature??
Thank You.
Lalit Kumar Barik
You'll want to take a look at the location secton of the web config.
In that section, you can define down to the page level the access rights, so it wouldn't matter if the users knew the URL of the secured pages, ASP.NET wouldn't let them in.
So you would add something like:
<location path="SecuredPage.aspx">
<system.web>
<authorization>
<deny users="?"/>
</authorization>
</system.web>
</location>
The "deny users="?"" bit says "Deny all anonymous users".
You can also set it up to only allow certain roles, if you are using those.
More information on the Authorization section can be found here:
authorization Element
This is food for the ASP.Net Membership services. Take a look at this article and also the great series over at 4GuysFromRolla.
Membership allows you to store user/password information which is used, among others, by the Login control. Coupled with the authorization configuration you will be able to directly narrow access to specific pages down to specific users or roles.
You will need a way to manage login sessions for each user. The following are some tutorials that could help you:
http://www.codeproject.com/KB/session/NoCookieSessionLogin.aspx
http://www.dotnetspider.com/resources/5597-Handling-Session-for-Login-Logout.aspx
You should verify the user's logged in state at every Page_Load() event on pages that must control permissions, or simply put the authentication code in a CS file that will be included in all other files.
Depending on the authentication architecture that you choose (simply use the session variable, or create a session id with cookies), you must adapt your code accordingly.
The simplest way would be to manage log-ins through the session object. When the user logs in properly with the right credentials, you can set Session["logged_in"] = true. And on every Page_Load() event of the pages you want to protect, you'd need to do the following check.
Add this code at the beginning of your Page_Load() function:
if (Session["logged_in"] != null && (bool)Session["logged_in"] == true){
Response.Write("I'm logged in!");
}else{
Response.Write("I'm not logged in.");
}
Please keep in mind that this is okay for simple intranet applications, but if you want to get into more secure login architectures, read up more about the subject, as reloying solely on session variables isn't safe because sessions can be highjacked.
I would make a role table for users. Everyone who logs in gets the 'normal' role. Special uses whom you designate by their credentials get assigned roles to access a page or section of your website. Certain users (like yourself) would get an administrator role that automatically allows them access to everything.
Fire off a function called CheckIsInRoles('Admin', 'Normal', 'WhateverRoleYouChoose') which returns a boolean. If true, load the page; if not, don't.
Even better don't display a link if not in the correct role.
This has the added benefit of everyone logging on once and then accessing all the pages they need to without having to log on each time.
Related
Scenario: I have the membership provider setup and its currently pointing to a SQL database on my machine. The role based access works and I have a menu that is security trimmed. The user can only get to pages that they have access to.
Problem: When an anonymous user tries to get to a page that they dont have access to it brings them to a login page so that they can login. That is fine. But when a logged in user tries to get to a page they dont have access to(Usually by typing in a URL) it brings them to the login page again asking them to login(except there already logged in. I'd like to either take them to a different page or somehow tell them they don't have access. Any ideas/suggestions?
Thanks in advance
This is what I use. They point out that using <customErrors> won't work because of the way the 401 status gets changed and provide a solution.
What are the ways to notify user that he does not have permissions to access a page?
What I already started is that I made an error page with "no permissions" message and user will be redirected if he does not have permissions on this page.
I don't know if this is the official or the best way.
Another place that what should I do in the UserControl case, for example, when I have a user control to browse the employees and I don't want to prevent the user in everytime the user control is used. I would prefer to process the permissions from one place (inside the user control's code).
Any ideas will be approciated.
Thanks.
I would suggest you make a custom page and redirect the user to that page if that user is not in certain role...
Put this condition in master page:
if (!(HttpContext.Current.User.IsInRole("Admin"))
{
Response.Redirect("UnAuthenticatedUser.aspx");
}
You have many options including:
Option1: Redirect user to a page that you have created for such purpose ..
Response.Redirect("ErrorPage.aspx");
Option2: Throw an exception then handle it in an appropriate way..
throw new Excepion("Exception Message");
I usualy set the value of the Visible property for the control that user does not have permissions on them to false .
You can use the authorization section in the web.config
It would all depend on how fine grained your permissions are. Based on permissions set, sometimes it may not make sense to show the entire page while other times, you need to disable and/or make readonly and/or hide part of UI. For example, lets say, there are two permissions, view user details and add/edit user details. So if view permission is not present then navigating to user details page, one should redirect user to a common error page stating something like "Insufficient Permissions". On the other hand, if view permission is there but no edit permission then one can see user details but button/links such as Edit/Detele should be hidden/disabled (or you may show user details in read-only format etc).
Typically, I prefer to fetch entire user permission set on login and cache it into application wide context classes (generally user specific context gets backed by session state). The permission set would have methods to check against specific permission. Then the base page (all pages would be derived from one common base page - intermediate base pages are possible for different concerns) would check if view permission for the page is present (the permission is obtained via a virtual method that interested page overrides to supply) and if not then user is redirected to common error page. Adjusting specific UI as per permissions is left to the individual pages (although there can be cases where pages may have common templates and even share that piece of code via another base page).
Im building an ASP website with user login. Does any one knows what is the best and must secure way to make login page and make pages restricted access? I know some ways and used them for some website but sometimes they were not that secure. There is couple access level for this website. Admin, User, Sales Team, and couple more. Thanks.
you can use session variables to store user level and then on asp code define what user can or can not see.
Or in database, I assume, you have field where level of access is defined as well.
Basically make your security level part of SQL query and show only data user should be able to see.
Basically you should have level of access in database, login page verify credentials and then store user level in session variable.
On any given page, while header loads, ASP retrives session variable and compare it to database.
If user have clearance to see that data he will if not-- display message that he is not authorized or redirect somewhere else where he can be.
Add an include file at the top of your ASP pages which is executed before any of the page's code. This way you can write your security code once, and apply it to all of your pages.
Assuming you are using IIS as your web server, you can let it handle your website security by using the different available authentication methods.
http://www.microsoft.com/technet/prodtechnol/WindowsServer2003/Library/IIS/9b619620-4f88-488b-8243-e6bc7caf61ad.mspx?mfr=true
http://www.authenticationtutorial.com/tutorial/
Perhaps the best authentication method for you would be Windows Integrated Authentication since it allows you to create groups (or maybe use the existing ones) to give access to certain directories or pages.
I am building a ASP.NET website that has members pages. I have created a folder where I keep the members pages in and that can only be accessed by logging in or creating a new account. The problem is how do I make the url of these members pages secure, so that someone cant simply give the url to another user for them to copy into a browser or bookmark. Any suggestions greatly appreciated.
In web.config you need specify that this folder for permitted user only.
To grant individual security (person against person) just add checking (for example at Page_Load) that member is permitted to see this page and throw HttException with code 403 (forbidden)
You can do this through the Authentication element in your web.config.
http://support.microsoft.com/kb/316871 has details on this but roughly you will add things that look like this:
<location path="subdir1">
<system.web>
<authorization>
<deny users="?" />
</authorization>
</system.web>
</location>
This will deny access to that subdir to all anonymous users.
To quote the MSDN page above:
When using forms-based authentication
in ASP.NET applications, only
authenticated users are granted access
to pages in the application.
Unauthenticated users are
automatically redirected to the page
specified by the loginUrl attribute of
the Web.config file where they can
submit their credentials. In some
cases, you may want to permit users to
access certain pages in an application
without requiring authentication.
Edit:
In response to your edit of testing user pages then there are two ways I can think of that this might work. If the page is specific to a given user then you can just make sure that in the code rather than getting the user details from the url that you look up who the logged in user is and give them their page. So for example if you are currently looking at members/mypage.aspx?user=bob then instead just link to members/mypage.aspx and in the code get the name of the logged in user to use. Then there is no way to tell the code that you want Bob's page without being Bob.
In the more likely event that you have groups of users (eg admin) that can see a page then you will need to put some code on your page to check permissions. For a given page you will need to work out who can view it somehow (eg by lookign up that page against the allowed user roles to get a list of roles) and then check if the logged in user is in that list of who can view (does the user have one of those roles.
eg Bob is an admin and Frank isn't. When going to your admin.aspx page you first of all lookup admin.aspx and find out that roles Admin and SuperAdmin are allowed to view it. You then look up the logged in user and iterate through their roles til you find one in the allowed roles list. If you find one process the page as normal, if you don't then either redirect somewhere else or throw an exception (eg throw your own MyAccessDeniedException that gets caught in your global event handler and shows a message explaining the user doesn't have permissions).
All of this can be done in a base class of your page to prevent you having to include the code on every page. That is you can create MyPage that inherits from Page and in the onload (or oninit or wherever you fancy) of MyPage run this security check. Then all the pages of your site inherit from MyPage instead of Page and you immediately get the functionality on all pages.
Hopefully this answers your questions.
Does anyone know of a way to get ASP.NET Forms Authentication to not redirect back to the login page if a user is not allowed to visit a certain page or folder based on their role (and perhaps show a message instead)?
The redirect happens because the user is not authorized to see the page - not because she is not authenticated with the system. As such, the framework does not distinct between the situation where a user is "not logged in" and the situation where she is just "missing the required role". If she does not have acccess, she is redirected to the login page - end of story.
What I usually do, is to create my login form with a MultiView with a view for each of the two cases, as well as one for the case where the user asked for the login form himself. Then I do something like this to toggle between the different views:
if (Request.QueryString["ReturnUrl"] == null)
myMultiView.ActiveViewIndex = 0; // user asked for login form
else if (Request.IsAuthenticated)
myMultiView.ActiveViewIndex = 1; // insufficient rights
else
myMultiView.ActiveViewIndex = 2; // login required
Rather than using a MultiView you could also insert a Response.Redirect in branch above, if this seems to make more sence in your application - e.g. if the three login forms are significantly diverse.
If you don't want it to redirect back to the login page, then what page do you want to resolve, the requested page, which they don't have access to? If so, and if you want that URL to be in their address bar, then you will need to override the base ASP.NET page, and prevent the continuation of rendering, and instead return an simple page with a pop up message or something.
I think you'll have to change the authorization in web.config for the given page's location so that everyone is authorized.
<configuration>
<location path="somepage.aspx">
<system.web>
<authorization>
<allow users="?"/>
</authorization>
</system.web>
</location>
</configuration>
Then you can use Roles.IsUserInRole() in the page logic to determine if they are authorized, and then display a message if they are not. I've done this before when I use the same aspx page for viewing and editing a record where anyone can view but only certain roles can edit.
4GuysFromRolla have a pretty detailed tutorial on how to use the membership provider. The link provided gives you details about how to apply user- and role-based authorization rules to methods and classes.
Hope this helps some.