Skip to content

Commit 0f07564

Browse files
authored
RDEV-3108 Usernames support, code simplification
1 parent 1ff9c9b commit 0f07564

File tree

10 files changed

+140
-111
lines changed

10 files changed

+140
-111
lines changed

Core/APIMethod.cs

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -17,8 +17,7 @@ public abstract class APIMethod
1717

1818
public static class RublonCommonParams
1919
{
20-
public const string FIELD_USER_ID = "appUserId";
21-
20+
public const string USERNAME_FIELD = "username";
2221
}
2322

2423
public RESTClient RestClient { get; set; }
@@ -43,10 +42,10 @@ public APIMethod(IRublonConsumer rublon)
4342
public void Perform()
4443
{
4544
var rawPostBody = string.Empty;
46-
var parameters = getParams();
47-
if (parameters != null && parameters.Count > 0)
45+
var requestBodyJSON = prepareRequestBody();
46+
if (requestBodyJSON != null && requestBodyJSON.Count > 0)
4847
{
49-
rawPostBody = parameters.ToString();
48+
rawPostBody = requestBodyJSON.ToString();
5049
}
5150

5251
var url = getUrl();
@@ -72,7 +71,7 @@ public void Perform()
7271
/// Get the API request's parameters object.
7372
/// </summary>
7473
/// <returns></returns>
75-
protected virtual JObject getParams()
74+
protected virtual JObject prepareRequestBody()
7675
{
7776
var parameters = new JObject();
7877
parameters.Add(FIELD_SYSTEM_TOKEN, rublon.SystemToken);

Properties/AssemblyInfo.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,5 +31,5 @@
3131
// You can specify all the values or you can default the Build and Revision Numbers
3232
// by using the '*' as shown below:
3333
// [assembly: AssemblyVersion("1.0.*")]
34-
[assembly: AssemblyVersion("1.0.2.0")]
35-
[assembly: AssemblyFileVersion("1.0.2.0")]
34+
[assembly: AssemblyVersion("1.1.0.0")]
35+
[assembly: AssemblyFileVersion("1.1.0.0")]

README.md

Lines changed: 23 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -49,8 +49,7 @@ e.g. with a username and password (usually we call it first factor).
4949
It is a necessary step, because upon Rublon's initialization the service
5050
must receive certain information about the user:
5151

52-
- a unique Id, stored in the system (inafter called **the integrated system**) implementing the Rublon service,
53-
- the user's email address.
52+
- the username, from Rublon for which authentication will be called, (usually it is the same as username from the integrated system).
5453

5554
To experience the full measure of two-factor authentication, the end-user
5655
should install the Rublon mobile app, available on all leading smartphone
@@ -64,15 +63,14 @@ a Email2FA process which does not require using an additional device of any kind
6463

6564
#### User protection
6665

67-
User protection is active when a user's email address in the integrated system
66+
User protection is active when a username in the integrated system
6867
can be matched to a user in the Rublon service.
69-
For this purpose, the user's email is sent to Rublon servers.
68+
For this purpose, the username is sent to Rublon servers.
7069

71-
1. If the email is matched to an existing Rublon account, the user's identity
70+
1. If the username is matched to an existing Rublon account, the user's identity
7271
can be confirmed using Rublon.
73-
2. Otherwise, if the user does not possess a Rublon account (the email
74-
could not be matched), Rublon will use the Email2FA process, trying to verify
75-
the user's identity by sending a confirmation email message to his email address.
72+
2. Otherwise, if the user does not possess a Rublon account (the username
73+
could not be matched), Rublon will start an enrollment process.
7674

7775
#### Identity confirmation
7876

@@ -160,7 +158,8 @@ An example of the library's initialization:
160158
var rublon = new Rublon(
161159
// system token:
162160
"A69FC450848B4B94A040416DC4421523",
163-
// secret key: "bLS6NDP7pGjg346S4IHqTHgQQjjSLw3CyApvz5iRjYzgIPN4e9EOi1cQJLrTlvLoHY8zeqg4ILrItYidKJ6JjEUZaA6pR1tZMwSZ"
161+
// secret key:
162+
"bLS6NDP7pGjg346S4IHqTHgQQjjSLw3CyApvz5iRjYzgIPN4e9EOi1cQJLrTlvLoHY8zeqg4ILrItYidKJ6JjEUZaA6pR1tZMwSZ"
164163
);
165164

166165
<a id="auth"></a>
@@ -179,42 +178,36 @@ Administrator can force users to authenticate using the mobile app (to avoid the
179178

180179
Authenticating a user with the second factor should be initiated when the user
181180
has successfully passed the first factor of authentication (e.g. the valid user
182-
credentials have been provided) and the user's unique Id and email address are known.
181+
credentials have been provided) and the user's unique Id is known.
183182

184-
The `Rublon.Auth()` method will check the user's protection status (using
185-
the email address) and return a URL address for the web browser to be redirected to
183+
The `Rublon.Auth()` method will check the user's protection status and return a URL address for the web browser to be redirected to
186184
(if user protection is active) or `null` in case the user's protection is not active.
187185

188186
<table>
189-
<caption><code>Rublon.Auth()</code> method arguments</caption>
187+
<caption><code>Rublon.Auth()</code> method has one argument of type <code>AuthenticationParameters</code> with the following fields</caption>
190188
<thead><tr>
191-
<th>Name</th>
189+
<th>Property Name</th>
192190
<th>Type</th>
193191
<th>Description</th>
194192
</tr></thead>
195193
<tbody>
196194
<tr>
197-
<td><code>callbackUrl</code></td>
195+
<td><code>CallbackUrl</code></td>
198196
<td>String</td><td>The integrated system's callback URL</td>
199197
</tr>
200198
<tr>
201-
<td><code>appUserId</code></td>
199+
<td><code>UserName</code></td>
202200
<td>String</td>
203-
<td>The integrated system's user's unique Id which will allow to log in the user upon successful authentication</td>
201+
<td>The integrated system's username, which will allow to log in the user upon successful authentication and match the user to a Rublon account.</td>
204202
</tr>
205203
<tr>
206-
<td><code>userEmail</code></td><td>String</td>
207-
<td>The user's email address in the integrated system which will allow to check the user's protection status and match the user to a Rublon account</td>
204+
<td><code>UserEmail</code></td><td>String</td>
205+
<td>The user's email address. This is a optional parameter and can be empty. If set the email addresss will be set in Rublon for the given username</td>
208206
</tr>
209207
<tr>
210-
<td><code>consumerParams</code></td>
208+
<td><code>AdditionalParams</code></td>
211209
<td>JSONObject</td>
212-
<td>Additional transaction parameters (optional)</td>
213-
</tr>
214-
<tr>
215-
<td><code>isPasswordless</code></td>
216-
<td>boolean</td>
217-
<td>Information if it is a login attempt using passwordless method (optional)</td>
210+
<td>Additional transaction parameters (optional), which will be send to Rublon, the ParamsBuilder class can be used to prepare parameters easily</td>
218211
</tr>
219212
</tbody>
220213
</table>
@@ -259,10 +252,10 @@ An example of logging in a user on an integrated system:
259252
260253
try { // Initiate a Rublon authentication transaction
261254
262-
String url = rublon.Auth(
263-
"http://example.com/rublon_callback", // callback URL
264-
Session.getUser().getId(), // User Id
265-
Session.getUser().getEmail() // User email
255+
String url = rublon.Auth(new AuthenticationParameters(){
256+
CallbackUrl = "http://example.com/rublon_callback",
257+
Username = Session.getUser().getId()
258+
}
266259
);
267260
268261
if (url != null) { // User protection is active

RublonSDK.csproj

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,7 @@
6969
<Compile Include="Properties\AssemblyInfo.cs" />
7070
<Compile Include="TwoFactor\API\BeginTransaction.cs" />
7171
<Compile Include="TwoFactor\API\Credentials.cs" />
72+
<Compile Include="TwoFactor\AuthenticationParameters.cs" />
7273
<Compile Include="TwoFactor\IRublon.cs" />
7374
<Compile Include="TwoFactor\Rublon.cs" />
7475
<Compile Include="TwoFactor\RublonCallback.cs" />

TwoFactor/API/BeginTransaction.cs

Lines changed: 23 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
using Newtonsoft.Json.Linq;
22
using Rublon.Sdk.Core;
3+
using System;
34

45
namespace Rublon.Sdk.TwoFactor
56
{
@@ -17,17 +18,17 @@ public class BeginTransaction : APIMethod
1718
protected string callbackUrl;
1819
protected string userEmail;
1920
protected string userId;
20-
protected JObject consumerParams;
21+
protected JObject additionalParams;
2122

2223
/// <summary>
2324
/// Construct the API method instance.
2425
/// </summary>
2526
/// <param name="rublon">Rublon instance.</param>
2627
/// <param name="callbackUrl">URL of the callback method.</param>
2728
/// <param name="userEmail">User's email address.</param>
28-
/// <param name="userId">User's local ID.</param>
29-
public BeginTransaction(Rublon rublon, string callbackUrl, string userEmail, string userId)
30-
: this(rublon, callbackUrl, userEmail, userId, new JObject())
29+
/// <param name="userName">User's local ID.</param>
30+
public BeginTransaction(Rublon rublon, string callbackUrl, string userEmail, string userName)
31+
: this(rublon, callbackUrl, userEmail, userName, new JObject())
3132
{
3233

3334
}
@@ -38,15 +39,15 @@ public BeginTransaction(Rublon rublon, string callbackUrl, string userEmail, str
3839
/// <param name="rublon">Rublon instance.</param>
3940
/// <param name="callbackUrl">URL of the callback method.</param>
4041
/// <param name="userEmail">User's email address.</param>
41-
/// <param name="userId">User's local ID.</param>
42-
/// <param name="consumerParams">Additional transaction parameters.</param>
43-
public BeginTransaction(IRublon rublon, string callbackUrl, string userEmail, string userId, JObject consumerParams)
42+
/// <param name="userName">User's local ID.</param>
43+
/// <param name="additionalParams">Additional transaction parameters.</param>
44+
public BeginTransaction(IRublon rublon, string callbackUrl, string userEmail, string userName, JObject additionalParams)
4445
: base(rublon)
4546
{
4647
this.callbackUrl = callbackUrl;
4748
this.userEmail = userEmail;
48-
this.userId = userId;
49-
this.consumerParams = consumerParams;
49+
this.userId = userName;
50+
this.additionalParams = additionalParams;
5051
}
5152

5253
/// <summary>
@@ -63,16 +64,23 @@ protected override string getUrl()
6364
return rublon.APIServer + REQUEST_URI_PATH;
6465
}
6566

66-
protected override JObject getParams()
67+
protected override JObject prepareRequestBody()
6768
{
68-
var baseParameters = base.getParams();
69-
var parameters = new JObject(consumerParams);
69+
var baseParameters = base.prepareRequestBody();
70+
var parameters = new JObject(additionalParams);
7071
parameters.Merge(baseParameters);
71-
parameters.Add(RublonCommonParams.FIELD_USER_ID, userId);
72+
parameters.Add(RublonCommonParams.USERNAME_FIELD, userId);
7273
parameters.Add(FIELD_CALLBACK_URL, callbackUrl);
73-
parameters.Add(FIELD_USER_EMAIL, userEmail.ToLower());
74-
74+
addUserEmailIfNotEmpty(parameters);
7575
return parameters;
7676
}
77+
78+
private void addUserEmailIfNotEmpty(JObject parameters)
79+
{
80+
if (!String.IsNullOrWhiteSpace(userEmail))
81+
{
82+
parameters.Add(FIELD_USER_EMAIL, userEmail.ToLower());
83+
}
84+
}
7785
}
7886
}

TwoFactor/API/Credentials.cs

Lines changed: 5 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -6,12 +6,7 @@ namespace Rublon.Sdk.TwoFactor
66
public class Credentials : APIMethod
77
{
88
public const string REQUEST_URI_PATH = "/api/transaction/credentials";
9-
10-
/// <summary>
11-
/// Field name for the user's device ID.
12-
/// </summary>
13-
public const string FIELD_DEVICE_ID = "deviceId";
14-
9+
1510
public const string FIELD_ACCESS_TOKEN = "accessToken";
1611

1712
protected string accessToken;
@@ -31,28 +26,19 @@ public Credentials(Rublon rublon, string accessToken)
3126
/// Get the user's local ID from the response.
3227
/// </summary>
3328
/// <returns></returns>
34-
public string GetUserId()
29+
public string GetUsername()
3530
{
36-
return methodCallResponse.Value<string>(RublonCommonParams.FIELD_USER_ID);
31+
return methodCallResponse.Value<string>(RublonCommonParams.USERNAME_FIELD);
3732
}
38-
39-
/// <summary>
40-
/// Get the user's device ID from the response.
41-
/// </summary>
42-
/// <returns></returns>
43-
public string GetDeviceId()
44-
{
45-
return methodCallResponse.Value<string>(FIELD_DEVICE_ID);
46-
}
4733

4834
protected override string getUrl()
4935
{
5036
return rublon.APIServer + REQUEST_URI_PATH;
5137
}
5238

53-
protected override JObject getParams()
39+
protected override JObject prepareRequestBody()
5440
{
55-
var baseParameters = base.getParams();
41+
var baseParameters = base.prepareRequestBody();
5642
baseParameters.Add(FIELD_ACCESS_TOKEN, accessToken);
5743

5844
return baseParameters;
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
using Newtonsoft.Json.Linq;
2+
3+
namespace Rublon.Sdk.TwoFactor
4+
{
5+
/// <summary>
6+
/// Authentication parameters used during transaction initialisation (transaction init).
7+
/// </summary>
8+
public class AuthenticationParameters
9+
{
10+
/// <summary>
11+
/// Url which Rublon will redirect browser, when authentication is finished
12+
/// </summary>
13+
public string CallbackUrl {
14+
get;
15+
set;
16+
}
17+
18+
/// <summary>
19+
/// Username of a user who is authenticated
20+
/// </summary>
21+
public string Username {
22+
get; set;
23+
}
24+
25+
/// <summary>
26+
/// Email of a user who is authenticated, this is optional
27+
/// </summary>
28+
public string UserEmail
29+
{
30+
get;
31+
set;
32+
} = "";
33+
34+
/// <summary>
35+
/// Additional parameters send to the transation init request
36+
/// </summary>
37+
public JObject AdditionalParams { get; set; } = new JObject();
38+
}
39+
}

TwoFactor/IRublon.cs

Lines changed: 25 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,33 @@ namespace Rublon.Sdk.TwoFactor
66
{
77
public interface IRublon : IRublonConsumer
88
{
9+
/// <summary>
10+
/// Provides logging feature, for debugging purposes its log method is called
11+
/// before and after every call to Rublon authentication server.
12+
/// </summary>
913
IRublonLogger Logger { get; set; }
1014

11-
string Auth(string callbackUrl, string userId, string userEmail);
12-
string Auth(string callbackUrl, string userId, string userEmail, JObject consumerParams);
15+
/// <summary>
16+
/// Initializes the Rublon 2-factor authentication transaction.
17+
/// Returns the URL to which browser should be redirected in order to continue authentication process for the started transaction.
18+
/// The URL will redirect to the so called Rublon prompt.
19+
/// If something will fail the method will throw exception which inherits from RublonException.
20+
/// When authentication process is finished in Rublon prompt the process will redirect to authenticationParameters.callbackUrl
21+
/// with access token and <see cref="GetCredentials(string)"/> can be called to finish authentication.
22+
/// Instead of get credentials you can also use <see cref="RublonCallback"/> which contains already some logic related to getting access token parameter.
23+
/// </summary>
24+
/// <param name="authenticationParameters">authentication parameters for the user</param>
25+
/// <returns>web URI to Rublon prompt for the created transaction</returns>
26+
string Auth(AuthenticationParameters authenticationParameters);
27+
28+
/// <summary>
29+
/// Finishes authentication for a given accessToken and get user's credentials using one-time use access token.
30+
///
31+
/// One-time use access token is a session identifier which will be deleted after first usage.
32+
/// This method can be called only once in authentication process.
33+
/// </summary>
34+
/// <param name="accessToken">access token</param>
35+
/// <returns>Credentials</returns>
1336
Credentials GetCredentials(string accessToken);
1437
}
1538
}

0 commit comments

Comments
 (0)