How to create a custom StudioSelector for Adam

The StudioSelector in Adam takes care of two major taks:

  • Single sign on for all the studios
  • Allow to user to go to a studio
When creating a custom StudioSelector, at least this functionality must be provided and this article guides you through the steps required to implement it.

Getting started

Open Visual Studio, create a new ASP.NET Web Application project and add the required Adam references:

  • Adam.Core
  • Adam.Tools
  • Adam.Web
  • Adam.Web.Core

To configure Adam properly for this web application, open the web.config file and add the configuration section definitions for Adam:

XML
1
2
3
4
5
6
7
8
9
<configSections> 
 <section name="Adam.Core" 
    type="Adam.Core.ConfigurationHandler,Adam.Core"/>
 <section name="Adam.Tools" 
    type="Adam.Tools.ConfigurationHandler,Adam.Tools"/>
 <section name="Adam.Web.Core" 
    type="Adam.Web.Core.Configuration.AdamWebConfiguration, Adam.Web.Core" 
    allowDefinition="Everywhere"/>
</configSections>

Specify the registration and application name to use in Adam. Since we are creating a custom studio selector, name this application "CustomStudioSelector". Beside this, specify how Adam should perform its logging:

XML
1
2
3
4
5
6
7
8
9
10
11
<Adam.Core>
 <defaultRegistration name="AdamNet"/>
 <applicationName name="CustomStudioSelector"/>
</Adam.Core>

<Adam.Tools>
 <logListeners>
  <add type="Adam.Tools.LogHandler.EventLogListener,Adam.Tools" 
       severity="Verbose"/>
 </logListeners>
</Adam.Tools>

And configure the web behavior of Adam as a custom StudioSelector

XML
1
2
3
4
5
6
7
8
9
10
11
12
13
14
<Adam.Web.Core>
 <websiteInfo 
      type="CustomStudioSelector" 
      title="CustomStudioSelector" 
      description="CustomStudioSelector" />
 <authentication 
      enabled="true"
      activeDirectoryAuthenticationProviderType="Adam.Core.Server.ActiveDirectoryAuthenticationProvider, Adam.Core"
      cookieName=".ADAMAUTH" 
      requireSSL="false" 
      persistentTimeout="30" 
      loginUrl="~/Login.aspx" 
      defaultUrl="~/Default.aspx"/>
</Adam.Web.Core>

Single sign on

To implement the single sign on feature in this custom studio selector, we need to modify the web.config file a bit more.

First, we need to ensure that the authentication cookie created by Adam can be parsed and decrypted by all studios. To enable this, you must configure the machineKey element in the system.web section properly  If all your studios are running in the same application pool, you can use the following configuration on all your studios:

XML
1
2
3
4
5
<machineKey 
     decryptionKey="AutoGenerate" 
     validationKey="AutoGenerate" 
     decryption="AES" 
     validation="SHA1" />

For more complex setups, you can find more information on the following MSDN page:
machineKey Element and How To: Configure MachineKey in ASP.NET 2.0 

Next, when need to make sure that the log off functionality is available to all studios. The log off itself is not the issue here (when the user clicks log off in any studio, the authentication cookie is cleared and no other studio can use it anymore). The real problem is the ASP.NET session management. If a user clicks log off in the asset studio, the ASP.NET session can be cleared in that studio, but the ASPNET session of the config studio is still available.

To deal with this problem, Adam creates an ASP.NET session id based upon the Adam session. This ensures that all studios use the same session id and when the user logs on again, his ASP.NET session id is changed. You can use the same behavior by setting the sessionIDManagerType in the se sessionState configuration element:

XML
1
2
3
<sessionState 
     sessionIDManagerType="Adam.Web.Core.MultiSiteSessionIDManager, 
                           Adam.Web.Core"/>

Another item to configure is how authentication is done and who is authorized to use this application.  Because the StudioSelector is the studio that performs a log on to Adam, you can configure this web application to use Adam authentication or Activve Directory authentication. For more information, see the help that came with your Adam installation.

The last step for providing the single sign on is the login page itself. Add a log Web Form to your application and name it Login.aspx and an Adamlogin control:

ASP.NET
1
<awc:AdamLogin runat="server" />

See the attached sample code project if you wish to customize the look and feel of the login control.

Log out

Of course, after the user performed a log in, he should be able to log off.

Because we configured everything needed for the single sign on above, it makes life pretty easy to implement the log off feature (this code will work in any studio):

C#
1
AdamAuthentication.SignOut();

Selecting a studio

The second feature that must be implemented in a custom studio selector is actually let the user select a studio.

To get the studios configured in Adam, a helper class can be used:

C#
1
ReadOnlyCollection<StudioInfo> allStudios = StudioHelper.GetStudios(true);

This method returns all studios configured in Adam, but does not take into account if a user has access to this studio. Checking this is easy: every studio has a role that indicates whether a user has access to it or not. This code checks whether the currently logged on user has access to the config studio:

C#
1
AdamHelper.GetApplication().HasRole("RoleAccessStudioConfigStudio");

A StudioInfo object contains the Name, Label and Url of the studio; there is no link to the image of the studio as you see on the default StudioSelector. However, all Adam studios have an 'icon.png' file in there root directory, which makes it pretty easy to create a link to the images (based upon the Url of the StudioInfo object).

An example of all this can be found in the Default.aspx page of the attached sample code project. The basic idea is to create a list of studios available to the user, bind this list to a GridView and use standard ASP.NET databinding to show the available studios.

Code Behind

C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
/// <summary>
/// Occurs when the page is loading and raises the Load event.
/// </summary>
/// <param name="e">The event data.</param>
protected override void OnLoad(EventArgs e)
{
  base.OnLoad(e);

  // When the page initially loads, data bind the grid view to the available studios.
  if (this.Page.IsPostBack == false)
  {
    // Get the studios for this user.
    ReadOnlyCollection<StudioInfo> oAllStudios = StudioHelper.GetStudios(true);

    // Filter out the studios that are not visible to the user.
    List<StudioInfo> oFilteredStudios = new List<StudioInfo>();
    foreach (StudioInfo oStudio in oAllStudios)
    {
      if (this.IsStudioVisible(oStudio.Name) == true)
        oFilteredStudios.Add(oStudio);
    }

    // Assign the filtered studios to the grid view.
    this.GridView1.DataSource = oFilteredStudios;
    this.GridView1.DataBind();
  }
}

/// <summary>
/// Helper method to determine wheter a studio is visible to the current user.
/// </summary>
/// <param name="name">The name of the studio to verify.</param>
/// <returns><b>true</b> when the user is allowed to see the studio; otherwise, <b>false</b>.</returns>
private Boolean IsStudioVisible(string name)
{
  // Check if name is 'studio selector'. If so, the studio is never visible.
  if (name.Equals("StudioSelector", StringComparison.InvariantCultureIgnoreCase))
    return false;
  // Check if the user has access to the studio.
  return AdamHelper.GetApplication().HasRole("RoleAccessStudio" + name, true);
}

Markup

ASP.NET
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<asp:GridView ID="GridView1" 
              runat="server" 
              AutoGenerateColumns="False">
  <Columns>
    <asp:ImageField 
           DataImageUrlField="Url" 
           DataImageUrlFormatString="{0}icon.png" 
           HeaderText="Icon" />
    <asp:HyperLinkField 
           DataNavigateUrlFields="Url" 
           DataTextField="Name" 
           HeaderText="Studio" />
    <asp:BoundField 
           DataField="Label" 
           HeaderText="Description" />
  </Columns>
</asp:GridView>

Wrap up

The sample code attached gives you a starting point to create your own custom studio selector. Now you can add more features to the studio selector, specific to meet the needs of your customer.

One of the things asked before is a 'forgot password' feature. This feature has been implemented in the sample code project attached to this article. Feel free to use it.

Sample Code

The article contains sample code project(s).
You must be logged in to view or download sample code.
Sign in now

Comments

Monday, 28 September 2009Michael Davies says
Hey guys, Useful article. We are now trying to do something more complex with the StudioInfo where we can add another attribute to the XML and we override StudioInfo to have that xtra attribute. Is there is any clues you can give us on how to do this?
Thursday, 18 June 2009Luc Naets says
Don't forget to add the App_Themes-folder from a standard Adam4 StudioSelector otherwise your project won't run.
Leave a comment
You must be logged in to post comments.
Sign in now
 
 
Technical
Business
rss feed