Beginning LightSwitch in VS 2012 Part 5: May I? Controlling Access with User Permissions
NOTE: This is the Visual Studio 2012 version of the popular Beginning LightSwitch article series. For other versions see:
- Visual Studio 2013 & HTML Client: Part 5: May I? Controlling Access with User Permissions
- Visual Studio 2010: Part 5: May I? Controlling Access with User Permissions
Welcome to Part 5 of the Beginning LightSwitch in Visual Studio 2012 series! In parts 1 thru 4 we learned about entities, relationships, screens and queries in Visual Studio LightSwitch. If you missed them:
- Part 1: What’s in a Table? Describing Your Data
- Part 2: Feel the Love. Defining Data Relationships
- Part 3: Screen Templates, Which One Do I Choose?
- Part 4: Too much information! Sorting and Filtering Data with Queries
In this post I want to talk about user permissions, also known as Access Control . In most business applications we need to limit what resources users can access in the system, usually because of different job function or role. For instance, only system administrators can add new users to the system. Certain data and screens in the application may be sensitive and should be restricted unless that user has rights to that part of the system. LightSwitch makes it easy to define user permissions and provides hooks on entities, screens and queries that allow you to check these permissions.
For a video demonstration on how to set up user permissions see: How Do I: Set Up Security to Control User Access to Parts of a Visual Studio LightSwitch Application?
Authentication & Authorization
There are two pieces of information LightSwitch applications need in order to determine which users have rights to what parts of the system. First, the system needs to verify the user accessing the application. This is called Authentication. In other words: “Prove you are who you say you are.” There are two supported types of authentication in LightSwitch; Windows and Forms.
Windows authentication means that the application trusts the user based on their Windows credentials. So once a user successfully logs into their Windows desktop, those credentials are automatically passed to the LightSwitch application. Forms authentication means that the application requests a username & password of its own, completely independent of any other credentials. So when you choose to use Forms authentication a login screen is presented to the user and they must type their username and password every time they want to access the application.
Once a user is authenticated, the application can determine access to parts of the system by reading their user permissions. This is called Authorization. In other words: “Now that I know who you are, here’s what you can do in the system.”
Setting Up User Permissions
It all starts on the Access Control tab of the Project Properties. To open it, right-click on the name of your project in the Solution Explorer and select “Properties” from the menu, or double-click on the “Properties” node under the project.
Then select the Access Control tab to specify the type of authentication you want to employ as well as what user permissions you want to define.
By default, the application doesn’t have authentication enabled so here is where you select the type of authentication you want to use.
Using Forms authentication means you will be storing usernames and encrypted passwords inside the LightSwitch database. This type of authentication is appropriate for internet-based applications where users are not on the same network and you need to support other operating systems besides Windows.
Using Windows authentication is appropriate if all your users are on the same network/domain or workgroup, like in the case of an internal line-of-business application. This means that no passwords are stored by your LightSwitch application. Instead the Windows logon credentials are used and passed automatically to the application. This is a more secure and convenient option if you can use it. In this case you can also choose whether you want to set up specific users and roles or whether any authenticated user has access to the application.
The best way to think of the two options for Windows authentication are:
- Give special permissions and roles to the Windows users or Active Directory groups that I administer within the application. (This is always on if you have selected Windows authentication)
- ALSO, let any Windows user access the unprotected parts of my application
Next you define user permissions that you check in code in order to access resources (we’ll work through an example next). There is always a SecurityAdministration permission defined for you that is used by LightSwitch once you deploy the application. When you deploy, LightSwitch will create a single user with this permission which gives them access to the screens necessary to define the rest of the users and roles in the system. However, while debugging your application, LightSwitch doesn’t make you log in because this would be tedious to do every time you built and ran (F5) the application. So instead you can use the “Granted for debug” checkbox to indicate which sets of permissions should be turned on/off in the debug session.
Let’s walk through a concrete example by implementing some security in our Address Book (Contact Manager) application we’ve been building in this series.
Checking User Permissions in the Address Book Application
Let’s start by selecting an authentication scheme. Since this application will be used by a small business to manage all their contacts, I’ll choose Windows authentication. I’ll also select “Allow any authenticated Windows user” into the system so that everyone in the company can search for and edit contacts by default. However, in order to add or delete contacts, users will need special permissions to do that.
So we need to create two new permissions. You can name the permissions whatever you want. You only see the name in code. When the system administrator sets up users and roles later, they will see the Display Name on the screen so be descriptive there. So add two permissions; CanAddContacts and CanDeleteContacts.
Next, leave the “Granted for debug” unchecked for both of those permissions so that we can test that they are working. When you leave this unchecked, the permission will not be granted. This allows us to easily test combinations of permissions while debugging. In order to see the Users and Roles screens while debugging you can enable it for SecurityAdministration. Now that we have these permissions set up here, we need to check them in code. As I mentioned, LightSwitch provides method hooks for you so you can write code when you need for all sorts of custom validation and business rules, including access control.
For more information on writing code in LightSwitch see the Performing Data-Related Tasks by Using Code topic in the library.
For more information on writing custom business rules see: Common Validation Rules in LightSwitch Business Applications
So in order to implement the security, we need to write a couple lines of code to check these permissions. LightSwitch provides access control methods on entities, screens and queries. To access these methods, drop down the “Write code” button on the top right of any designer and you will see an “Access Control Methods” section in the list. When you want to restrict viewing (reading), inserting (adding), editing or deleting entities, open the entity in the Data Designer and drop down the “Write code” button and select the appropriate access control method.
For this application, select the Contacts_CanDelete method and this will open the code editor to that method stub. All you need to do is write one line of code (in bold below) to check the CanDeleteContacts permission you set up:
VB:
Namespace LightSwitchApplication
Public Class ApplicationDataService
Private Sub Contacts_CanDelete(ByRef result As Boolean)
'Add this one line of code to verify the user has permission to delete contacts: result = Me.Application.User.HasPermission(Permissions .CanDeleteContacts)
End Sub
End Class
End Namespace
C#:
namespace LightSwitchApplication
{
public partial class ApplicationDataService
{
partial void Contacts_CanDelete(ref bool result)
{
//Add this one line of code to verify the user has permission to delete contacts:
result = this.Application.User.HasPermission(Permissions .CanDeleteContacts);
}
}
}
Now go back to the “Write Code” button on the designer and select Contacts_CanInsert and then similarly write the following line of code (in bold) to check the CanAddContacts permission. Your code file should look like this.
VB:
Namespace LightSwitchApplication
Public Class ApplicationDataService
Private Sub Contacts_CanDelete(ByRef result As Boolean)
'Add this one line of code to verify the user has permission to delete contacts:
result = Me.Application.User.HasPermission(Permissions.CanDeleteContacts)
End Sub
Private Sub Contacts_CanInsert(ByRef result As Boolean)
'Add this one line of code to verify the user has permission to add contacts: result = Me.Application.User.HasPermission(Permissions.CanAddContacts)
End Sub
End Class
End Namespace
C#:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.LightSwitch;
using Microsoft.LightSwitch.Security.Server;
namespace LightSwitchApplication
{
public partial class ApplicationDataService
{
partial void Contacts_CanDelete(ref bool result)
{
//Add this one line of code to verify the user has permission to delete contacts:
result = this.Application.User.HasPermission(Permissions.CanDeleteContacts);
}
partial void Contacts_CanInsert(ref bool result)
{
//Add this one line of code to verify the user has permission to delete contacts:
result = this.Application.User.HasPermission(Permissions .CanAddContacts);
}
}
}
You may be wondering why we are checking these permissions in the entity instead of the screens. Checking permissions in the entity guarantees that no matter what screen the user is working with, the data actions are protected. It’s best practice remember to secure your entities first if you need to implement user permissions in your application. However, our application also has a “Create New Contact” screen and we don’t want to show this to the user on the menu if they do not have permission to add contacts to the system. If we forget to hide this screen from the menu, then the user would be able to open it and fill it out with data. However, when they click Save the Contacts_CanInsert method above will run and prevent the actual data from saving.
So in order to hide this screen from the navigation menu, we need to add one more check. Double-click the CreateNewContact screen in the Solution Explorer to open the Screen Designer. Drop down the “Write Code” button on the top right and you will see the one Access Control method available to you for screens:
Select the CreateNewContact_CanRun method and then write the following line of code (in bold):
VB:
Namespace LightSwitchApplication
Public Class Application
Private Sub CreateNewContact_CanRun(ByRef result As Boolean)
'Add this one line of code to verify the user has permission to run the screen: result = Me.User.HasPermission(Permissions.CanAddContacts)
End Sub
End Class
End Namespace
C#:
namespace LightSwitchApplication
{
public partial class Application
{
partial void CreateNewContact_CanRun(ref bool result)
{
//Add this one line of code to verify the user has permission to run the screen: result = this.User.HasPermission(Permissions .CanAddContacts);
}
}
}
Run it!
Now we are ready to test the application so build and run by hitting F5. Because we didn’t grant the CanAddContacts and CanDeleteContacts permissions for debug you will notice first that the CreateNewContact screen is not showing up on the menu. The first screen that displays is the custom search screen we created in Part 4. If you click on a contact then the details screen will open which allows the user to edit that contact’s information. In order to see if we are restricted from deleting or adding new contacts let’s make a small change to the search screen. While the search screen is open click the “Design Screen” button at the bottom right to open the screen customization mode.
In the content tree on the left, expand the command bar under the Data Grid and add two commands; DeleteSelected and AddAndEditNew.
Click Save (ctrl+shift+S) to save and exit customization mode and notice that the commands are now disabled. Since we do not have permission to add or delete contacts this behavior is correct. Also since we are checking these permissions at the entity level all screen commands behave appropriately with no additional code necessary. If you go back to your project properties Access Control tab you can check off combinations of permissions you want to test and you will see all commands enable/disable appropriately.
Users & Roles Screens
Before we wrap up I want to quickly walk through the Users and Roles screens. When you enable the SecurityAdministration permission for debugging, these screens are available on the menu. However, keep in mind that the data you put into these screens isn’t used at debug time. It isn’t later until you deploy the application when these screens are used. So putting data into these screens is for demonstration purposes only. When your application is deployed the first time, LightSwitch will ask you for an administrator username & password that it deploys into the users table and grants the SecurityAdministration permission. That administrator can then enter the rest of the users into the system.
First you define roles and add the permissions you defined to that role using the Roles Screen.
Then you can add new users and Active Directory groups using the Users Screen and assign them the appropriate Roles. If you assign a role to an AD group and then add a user that is part of that group to the system, LightSwitch will indicate which roles are being inherited from the groups to which the user belongs.
Wrap Up
As you can see defining and checking user permissions in Visual Studio LightSwitch is a simple but important task. Access control is a very common requirement in professional business applications and LightSwitch provides an easy to use framework for locking down all parts of the application through method hooks on entities, screens and queries. Once you deploy your application, the system administrator can start setting up users and roles to control access to the secure parts of your application.
For more information on user permissions and deploying applications see Working with User Permissions and Deploying LightSwitch Applications topics on the LightSwitch Developer Center.
In the next post we’ll look at themes and how to change the look and feel of your application by installing LightSwitch extensions. We’ll look at what’s available for free as well as some inexpensive ones that really look great. Until next time!
Enjoy!
Read the next article –> Beginning LightSwitch in VS 2012 Part 6: Go beyond the box. Customizing LightSwitch Apps with Extensions
Comments
Anonymous
May 06, 2013
Hi, Thank you for all of your wonderful articles and videos. I'm curious about being able to store and use asp.net user profile data. Is there any way you could point me in the right direction?Anonymous
July 08, 2013
How can I visualize the Login Screen without deploy the application [Generate the installer]? it is posible? thanks!Anonymous
July 09, 2013
@agupta - Check out this article on creating your own provider: blogs.msdn.com/.../customizing-lightswitch-user-management.aspx Another easier option is to just create your own Users table in your data model and then create a query based on the username to relate that information to the security data. @Harden Yasser - check out the last section in the article above. "When you enable the SecurityAdministration permission for debugging, these screens are available on the menu." Just keep in mind that the data you enter while debugging will not be deployed with the app. HTH, -BethAnonymous
January 23, 2014
@Beth - I cannot seem to get any of your examples to work with my HTML Client for setting up security? All I am trying to do is create a browse screen and allow any windows domain user to be able to see the results of the query. I have enabled Windows Authentication, I have 2 permissions specified CanRead and CanEdit. Where I am getting lost is how you tie a windows domain group to these permissions, there seems to be a step missing in the documentation or that I am overlooking. I have granted permission at the SQL Server level. I am also using VS 2013. Is there any chance of some new videos or professional training for lightswitch and vs 2013?Anonymous
January 23, 2014
Hi Ken, You'll want to read the VS2013 version of this article that shows how to do this with the HTML client. blogs.msdn.com/.../beginning-lightswitch-in-vs-2013-part-5-may-i-controlling-access-with-user-permissions.aspx You need to add the administration console to manage user permissions once you deploy. Also keep in mind your users must be running IE on Windows in order to use Windows Auth. Forms Auth may be a better solution for the HTML client as that will allow access from any HTML5-capable browser or mobile device. blogs.msdn.com/.../how-to-assign-users-roles-and-permissions-to-a-lightswitch-html-mobile-client.aspx Cheers, -BethAnonymous
February 13, 2014
Hi Beth, I Just need to get all online users and give the admin the ability to blockunblock any of them for a while, do you have any ideas?Anonymous
June 03, 2014
Hi Beth, I have created LS app and I have one problem. I want to show Login Form, but allways I see HomeScreen (in app I have one screen) and there is Test User. I use Forms authentication. Is is possible in debud mode (without publishing) launch Login forms? Thanks for all.Anonymous
June 04, 2014
@Julo - In order to see the Users and Roles screens while debugging you can enable "Granted for debug" for SecurityAdministration. However, note that any data you put into these screens will not be deployed with your application when you publish it.Anonymous
October 29, 2014
Hi Beth, I m using VS 2013, I can't find this access control method "Can_Run". Any idea?Anonymous
May 04, 2017
It's impressive that you are getting ideas from this paragraph as well as from our dialogue made at this place.