In this post, Bryan Baker describes a new security sample he contributed to EDN:
A new developer sample that demonstrates security techniques for the Web ADF is available at the ESRI Developer Network. This sample will also be available as part of the installed software developer kit (SDK) samples with the next service pack of ArcGIS Server.
This sample shows some ways to restrict access to GIS resources and functionality based on the user’s login. While access may be restricted in a variety of ways, the sample takes this approach:
- All users must log in before they can access the web application. Users are redirected to a login page to log in.
- Once logged in, users see the main website page with map, table of contents, etc. This sample uses a simple set of web controls rather than the full Web Mapping Application template, but the same techniques could be applied to the template.
- Content varies depending on the role (group) in which the user is a member. This sample has a Managers role. Users in this role see all content added to the web application. If the user is not in this role, the following content is hidden:
- A map layer (highways) is hidden and its entry is removed from the table of contents.
- An item is removed from the toolbar. This item is a command that displays information about map layers and fields.
- Two query tasks are removed from the page.
- ASP.NET controls are used to display the user’s login name, and to display hyperlinks to log out, to change the user’s password, and to create a new account from the login page.
The upcoming version 9.3 of ArcGIS Server will feature out-of-the-box security in ArcGIS Server Manager. Those features will enable you to require users to log in to access services or web applications. However, those will not include the ability to restrict access to specific functionality and layers within a web application, based on the identity of the user. So the techniques in this sample will be relevant for both 9.2 and 9.3.
The introduction page to the sample at EDN contains more information on the sample. Standard ASP.NET techniques provided the functionality for all of the security aspects of the sample. Note that this sample is limited to restrict content to authorized users. It does not cover other aspects of security, such as encrypting traffic between user and server using secure sockets layer (SSL, using HTTPS), or checking user input for invalid values. Many websites have information about these other important aspects of securing web applications.
Some details on the sample
For those of you who might be interested, read on for some discussion of how security is implemented in this sample. First we cover how we require all users to log in in order to access the site. Then we’ll see how resources and functionality differ depending on who the user is.
Require users to log in
We require all users to log in in order to access the application. We could set this up manually in code, but a built-in tool makes it easier: the Web Site Administration Tool (WSAT). This ASP.NET tool is available from Visual Studio (or Visual Web Developer Express). After we open the website for which we want to set security, we can open WSAT from Visual Studio’s Website menu. This web-based administrative tool allows us to set up and manage security for our web application.
In the main WSAT menu, we choose Security. WSAT displays two options for access: from the Internet and from a local network. These translate into where the users are stored. The local-network option means users are Windows users on the local server or on the domain. This option also typically means that users visiting the site will be prompted for their login by a pop-up dialog in the browser. While the local-network option is the default when creating a new ASP.NET web application, most websites use the second option (“from the Internet”), which means users are stored in a database or other external location. This way we can provide the typical web page form that users fill out to log in. Behind the scenes, this choice sets an authentication element in the web.config file of the website:
<authentication mode="Forms" />
Also behind the scenes, setting the authentication type sets up a database within our web application. By default, WSAT creates a SQL Server Express database within the App_Data folder of our website. This database is specific to this web application. It is possible to use a database outside the web application, including a database in the full SQL Server or another database. See documentation or websites on ASP.NET for information. For our sample, we use the default application-level database.
Once we choose our authentication type, we see the web page that allows us to manage the access security for our site. We will not go through the steps individually here, but we used this page to create our users, enable roles, add roles, and assign users to roles. Roles allow us to manage security without adding or removing users individually to access rules when people enter or leave the organization or change positions within the organization. All these users and roles are stored in our SQL Server Express database.
Finally in WSAT, we create access rules for our website. These rules determine who can access our website. We used a simple rule: anyone can obtain access to the website as long as they have a user account. All we need to do is to prevent access by anonymous users. We do that by clicking the Create access rules hyperlink, and in the add-access-rule page, we select Anonymous users, ensure that “Deny” is selected, and click OK.
Again behind the scenes, this adds an authorization element to the web.config file of the web application:
<deny users="?" />
This element instructs the application to not allow anonymous users (indicated by the “?”) to access the website.
Now our application will require users to log in, and it will get their login from a form. We just need to provide the form for logging in. Fortunately, ASP.NET 2.0 (and above) makes this easy. We just create a new page within the website and name it login.aspx. By default, ASP.NET will look for this page and use it. In Visual Studio, we drag a Login web control onto this login.aspx page, and save it. That’s all that’s required to create a login page, though we added a few touches to ours, as you can see if you download the sample.
Display content based on user role
Now that users are logged in, we display different content depending on their roles. The approach in this sample is to add all functionality and content at design time in Visual Studio, and then remove items with runtime code where appropriate. We could also add new functionality for particular users at runtime, but the sample does not show that option.
In our server-side code, we can get information about the user and modify page content. In the sample, this happens in the Page_PreRenderComplete method. The code to check the user’s role is simple:
private string fullyEnabledRole = "Managers";
// modify page content for role
The User object tells us the user name and also whether the user is a member of a particular role. In this case, we check whether the user is in the Managers role. If not, we insert code to modify the page content. In the sample, we have three methods (Subs) that are called within the if statement shown above:
- HideLayer() – hides a specific map layer in the Map and Toc (table of contents) controls
- RemoveItemFromToolbar() – removes a specific item from a toolbar
- RemoveTask() – removes a task from the TaskManager and associated Menu
Finally, we added one other example of setting content based on role. Rather than using code, we used the ASP.NET LoginView control. This control allows you to easily show or hide content based on whether the user is logged in, or if the user is in a particular role. To set up the LoginView control in Visual Studio, you select the view where you want to show some content, and drag the content into the LoginView control. In our case, we created a “RoleGroup” for Managers using the “smart tag” on the LoginView control. Then we dragged a QueryAttributes task into the control. This way, ASP.NET automatically displays the task when someone in Managers is logged in, and hides it from everyone else. The only down side of the LoginView control is that you cannot use it with the TaskManager/Menu option as in the standard Web Mapping Application template. For that case you must use the approach as we did in the RemoveTask() method discussed above.
We hope this sample shows that it is possible, and for some items relatively easy, to add security to your web application. You can secure the entire website, so that all users must log in for any access. You can also secure specific aspects of your application, such as map layers or tasks, based on the user’s role.