Recently I worked on a customized self-service password reset (SSPR) solution leveraging FIM 2010 R2. The SSPR functionality provided out of the box by FIM 2010 R2 is quite comprehensive. In the design sessions with the customer, they decided that they wanted to use a higher level of security for users on the Internet to be able to reset their passwords. This certainly makes sense—exposing an interface where corporate users can reset their passwords is a boon to the service desk, but introduces a significant threat surface and associated security risk.
What we need to do is to ensure the person resetting the password is actually the user and not a malicious person or agent. The primary authentication method for the reset involves the user answering a series of questions that only they know the answer to. You see this method in use quite frequently these days. However, this satisfies just one mechanism of authentication (called a “factor”), something the user knows. Higher security is gained by adding another factor: for example, something (physical) that the user has in their possession.
A similar but not precisely a two-factor method is to leverage an “out of band” channel to send a code to a user, which they will enter only once, during this particular password reset. Not surprisingly this is called a one-time password (OTP). An obvious channel and by far the most common is sending this one-time password to a user’s personal email address. (We might consider “possession” of the separate email address and access to it a 2nd factor, but it’s not the same as having a physical smart card, a key fob, or dongle.) However, a user’s cell phone is definitely a physical factor which presumably the user will keep in their possession.
Fortunately FIM’s SSPR feature has the capability to send an OTP, and can send it in a number of ways via custom extension code. Users can be challenged with a one-time password either via an alternate email address or by an SMS text message. The text message is what we decided was the best choice for the organization.
So, how can FIM send SMS messages? Well, we do need to have an SMS service provider that can receive and route the messages appropriately. One such Internet-based provider is Twilio. Twilio provides a RESTful web service and a published API allowing for easy integration with applications. I was very impressed with the simplicity and performance of their SMS API. Pricing is very attractive as well. That’s beyond the scope of this post, but I’d venture that any size organization can afford it.
So, how do we make this work with FIM? Well, FIM provides an interface via the Microsoft.IdentityManagement.SmsServiceProviderContract assembly included with FIM. The process is laid out in this TechNet article.
So let’s take a look at an example of how to use the Twilio API:
using Twilio;
class Example
{
static void Main(string[] args)
{
// your Account Sid and Auth Token are found in your account information online
string AccountSid = ” BD7eb96075d6bf7377c05f8bcf25a5294b”;
string AuthToken = “”;
var twilio = new TwilioRestClient(AccountSid, AuthToken);
var message = twilio.SendMessage(“+14158141829”, “+15558675309”, “Jenny please?! I love you <3”, newstring[] {“https://www.example.com/hearts.png”});
Console.WriteLine(message.Sid);
}
}
It’s really that easy, and that’s one reason we chose Twilio over several other options.
So, for FIM SSPR, we need to create the SmsServiceProvider dll that FIM will use and leverage this API. The relevant code looks something like this:
using Microsoft.IdentityManagement.SmsServiceProvider;
using Twilio;
public class SmsServiceProvider : ISmsServiceProvider
{
public void SendSms(string mobileNumber,
string message,
Guid requestId,
Dictionary<string, object> deliveryAttributes)
{
mySMSProvider.SendSms(mobileNumber, message);
}
}
class mySMSProvider
{
static string AccountSid = “BD7eb96075d6bf7377c05f8bcf25a5294b”;
static string AuthToken = “58a93f5d342e842dc572ab131af83757”;
mySMSProvider()
{
}
public static int SendSms(string userMobileNumber, string message)
{
Int32 result;
string error;
// instantiate a new Twilio Rest Client
var client = new TwilioRestClient(AccountSid, AuthToken);
var transaction = client.SendMessage(
“678-967-4113”, // “From” number, must be an SMS-enabled Twilio number
userMobileNumber, // “To” number, if using Sandbox see note above
// message content, passed in as a parameter from FIM
message);
}
…
We also need to create a password reset workflow that uses the OTP gate and handle a few other configuration details, of course.
We know that the sophistication of automated attacks, password cracking techniques, and the frequency of those attacks on high-value targets, it’s more important than ever for an organization to balance efficient operations with adequate security measures. The frequency of security breaches seen recently points clearly to the need for strong authentication such as one-time passwords in SSPR.