Skip to content

Commit a193697

Browse files
committed
Introduce OpenIdAuthenticationMessage.GetParameters() and make Parameters protected
1 parent 3041cd0 commit a193697

File tree

3 files changed

+119
-54
lines changed

3 files changed

+119
-54
lines changed

src/AspNet.Security.OpenId.Steam/SteamAuthenticationHandler.cs

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,13 +22,18 @@ namespace AspNet.Security.OpenId.Steam
2222
{
2323
public class SteamAuthenticationHandler : OpenIdAuthenticationHandler<SteamAuthenticationOptions>
2424
{
25-
public SteamAuthenticationHandler(IOptionsMonitor<SteamAuthenticationOptions> options, ILoggerFactory logger, UrlEncoder encoder, ISystemClock clock)
25+
public SteamAuthenticationHandler(
26+
[NotNull] IOptionsMonitor<SteamAuthenticationOptions> options,
27+
[NotNull] ILoggerFactory logger,
28+
[NotNull] UrlEncoder encoder,
29+
[NotNull] ISystemClock clock)
2630
: base(options, logger, encoder, clock)
27-
{ }
31+
{
32+
}
2833

2934
protected override async Task<AuthenticationTicket> CreateTicketAsync(
3035
[NotNull] ClaimsIdentity identity, [NotNull] AuthenticationProperties properties,
31-
[NotNull] string identifier, [NotNull] IDictionary<string, string> attributes)
36+
[NotNull] string identifier, [NotNull] IReadOnlyDictionary<string, string> attributes)
3237
{
3338
var principal = new ClaimsPrincipal(identity);
3439
var ticket = new AuthenticationTicket(principal, properties, Scheme.Name);

src/AspNet.Security.OpenId/OpenIdAuthenticationHandler.cs

Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,9 @@ public OpenIdAuthenticationHandler(
2727
[NotNull] ILoggerFactory logger,
2828
[NotNull] UrlEncoder encoder,
2929
[NotNull] ISystemClock clock)
30-
: base(options, logger, encoder, clock) { }
30+
: base(options, logger, encoder, clock)
31+
{
32+
}
3133
}
3234

3335
public class OpenIdAuthenticationHandler<TOptions> : RemoteAuthenticationHandler<TOptions>
@@ -38,7 +40,9 @@ public OpenIdAuthenticationHandler(
3840
[NotNull] ILoggerFactory logger,
3941
[NotNull] UrlEncoder encoder,
4042
[NotNull] ISystemClock clock)
41-
: base(options, logger, encoder, clock) { }
43+
: base(options, logger, encoder, clock)
44+
{
45+
}
4246

4347
protected override async Task<HandleRequestResult> HandleRemoteAuthenticateAsync()
4448
{
@@ -145,7 +149,7 @@ protected override async Task<HandleRequestResult> HandleRemoteAuthenticateAsync
145149
name: OpenIdAuthenticationConstants.Parameters.State, value: state);
146150

147151
// Validate the return_to parameter by comparing it to the address stored in the properties.
148-
// See http://openid.net/specs/openid-authentication-2_0.html#verify_return_to
152+
// See http://openid.net/specs/openid-authentication-2_0.html#verify_return_to for more information.
149153
if (!string.Equals(message.ReturnTo, address, StringComparison.Ordinal))
150154
{
151155
return HandleRequestResult.Fail("The authentication response was rejected because the return_to parameter was invalid.");
@@ -216,7 +220,7 @@ protected override async Task<HandleRequestResult> HandleRemoteAuthenticateAsync
216220

217221
protected virtual async Task<AuthenticationTicket> CreateTicketAsync(
218222
[NotNull] ClaimsIdentity identity, [NotNull] AuthenticationProperties properties,
219-
[NotNull] string identifier, [NotNull] IDictionary<string, string> attributes)
223+
[NotNull] string identifier, [NotNull] IReadOnlyDictionary<string, string> attributes)
220224
{
221225
var principal = new ClaimsPrincipal(identity);
222226
var ticket = new AuthenticationTicket(principal, properties, Scheme.Name);
@@ -319,7 +323,10 @@ protected override async Task HandleChallengeAsync(AuthenticationProperties prop
319323
value: string.Join(",", Options.Attributes.Select(attribute => attribute.Key)));
320324
}
321325

322-
var address = QueryHelpers.AddQueryString(configuration.AuthenticationEndpoint, message.Parameters);
326+
var address = QueryHelpers.AddQueryString(configuration.AuthenticationEndpoint,
327+
message.GetParameters()
328+
.ToDictionary(parameter => parameter.Key,
329+
parameter => parameter.Value));
323330

324331
Response.Redirect(address);
325332
}
@@ -349,7 +356,7 @@ private async Task<bool> VerifyAssertionAsync([NotNull] OpenIdAuthenticationMess
349356
};
350357

351358
// Copy the parameters extracted from the assertion.
352-
foreach (var parameter in message.Parameters)
359+
foreach (var parameter in message.GetParameters())
353360
{
354361
if (string.Equals(parameter.Key, $"{OpenIdAuthenticationConstants.Prefixes.OpenId}." +
355362
OpenIdAuthenticationConstants.Parameters.Mode, StringComparison.Ordinal))

src/AspNet.Security.OpenId/OpenIdAuthenticationMessage.cs

Lines changed: 98 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66

77
using System;
88
using System.Collections.Generic;
9-
using System.Linq;
9+
using System.Collections.ObjectModel;
1010
using JetBrains.Annotations;
1111
using Microsoft.Extensions.Primitives;
1212

@@ -20,10 +20,7 @@ public class OpenIdAuthenticationMessage
2020
/// <summary>
2121
/// Initializes a new OpenID message.
2222
/// </summary>
23-
public OpenIdAuthenticationMessage()
24-
: this(new Dictionary<string, string>())
25-
{
26-
}
23+
public OpenIdAuthenticationMessage() { }
2724

2825
/// <summary>
2926
/// Initializes a new OpenID message.
@@ -36,7 +33,15 @@ public OpenIdAuthenticationMessage([NotNull] IDictionary<string, string> paramet
3633
throw new ArgumentNullException(nameof(parameters));
3734
}
3835

39-
Parameters = parameters;
36+
foreach (var parameter in parameters)
37+
{
38+
if (string.IsNullOrEmpty(parameter.Key))
39+
{
40+
continue;
41+
}
42+
43+
Parameters.Add(parameter.Key, parameter.Value);
44+
}
4045
}
4146

4247
/// <summary>
@@ -50,92 +55,134 @@ public OpenIdAuthenticationMessage([NotNull] IEnumerable<KeyValuePair<string, St
5055
throw new ArgumentNullException(nameof(parameters));
5156
}
5257

53-
Parameters = parameters.ToDictionary(
54-
parameter => parameter.Key,
55-
parameter => (string) parameter.Value);
58+
foreach (var parameter in parameters)
59+
{
60+
if (string.IsNullOrEmpty(parameter.Key))
61+
{
62+
continue;
63+
}
64+
65+
Parameters.Add(parameter.Key, parameter.Value);
66+
}
5667
}
5768

5869
/// <summary>
5970
/// Gets or sets the openid.claimed_id property.
6071
/// </summary>
6172
public string ClaimedIdentifier
6273
{
63-
get { return GetParameter(OpenIdAuthenticationConstants.Parameters.ClaimedId); }
64-
set { SetParameter(OpenIdAuthenticationConstants.Parameters.ClaimedId, value); }
74+
get => GetParameter(OpenIdAuthenticationConstants.Parameters.ClaimedId);
75+
set => SetParameter(OpenIdAuthenticationConstants.Parameters.ClaimedId, value);
6576
}
6677

6778
/// <summary>
6879
/// Gets or sets the openid.identity property.
6980
/// </summary>
7081
public string Identity
7182
{
72-
get { return GetParameter(OpenIdAuthenticationConstants.Parameters.Identity); }
73-
set { SetParameter(OpenIdAuthenticationConstants.Parameters.Identity, value); }
83+
get => GetParameter(OpenIdAuthenticationConstants.Parameters.Identity);
84+
set => SetParameter(OpenIdAuthenticationConstants.Parameters.Identity, value);
7485
}
7586

7687
/// <summary>
7788
/// Gets or sets the openid.error property.
7889
/// </summary>
7990
public string Error
8091
{
81-
get { return GetParameter(OpenIdAuthenticationConstants.Parameters.Error); }
82-
set { SetParameter(OpenIdAuthenticationConstants.Parameters.Error, value); }
92+
get => GetParameter(OpenIdAuthenticationConstants.Parameters.Error);
93+
set => SetParameter(OpenIdAuthenticationConstants.Parameters.Error, value);
8394
}
8495

8596
/// <summary>
8697
/// Gets or sets the openid.mode property.
8798
/// </summary>
8899
public string Mode
89100
{
90-
get { return GetParameter(OpenIdAuthenticationConstants.Parameters.Mode); }
91-
set { SetParameter(OpenIdAuthenticationConstants.Parameters.Mode, value); }
101+
get => GetParameter(OpenIdAuthenticationConstants.Parameters.Mode);
102+
set => SetParameter(OpenIdAuthenticationConstants.Parameters.Mode, value);
92103
}
93104

94105
/// <summary>
95106
/// Gets or sets the openid.ns property.
96107
/// </summary>
97108
public string Namespace
98109
{
99-
get { return GetParameter(OpenIdAuthenticationConstants.Parameters.Namespace); }
100-
set { SetParameter(OpenIdAuthenticationConstants.Parameters.Namespace, value); }
110+
get => GetParameter(OpenIdAuthenticationConstants.Parameters.Namespace);
111+
set => SetParameter(OpenIdAuthenticationConstants.Parameters.Namespace, value);
101112
}
102113

103114
/// <summary>
104115
/// Gets or sets the openid.realm property.
105116
/// </summary>
106117
public string Realm
107118
{
108-
get { return GetParameter(OpenIdAuthenticationConstants.Parameters.Realm); }
109-
set { SetParameter(OpenIdAuthenticationConstants.Parameters.Realm, value); }
119+
get => GetParameter(OpenIdAuthenticationConstants.Parameters.Realm);
120+
set => SetParameter(OpenIdAuthenticationConstants.Parameters.Realm, value);
110121
}
111122

112123
/// <summary>
113124
/// Gets or sets the openid.return_to property.
114125
/// </summary>
115126
public string ReturnTo
116127
{
117-
get { return GetParameter(OpenIdAuthenticationConstants.Parameters.ReturnTo); }
118-
set { SetParameter(OpenIdAuthenticationConstants.Parameters.ReturnTo, value); }
128+
get => GetParameter(OpenIdAuthenticationConstants.Parameters.ReturnTo);
129+
set => SetParameter(OpenIdAuthenticationConstants.Parameters.ReturnTo, value);
119130
}
120131

121132
/// <summary>
122133
/// Gets the parameters associated with this OpenID message.
123134
/// </summary>
124-
public IDictionary<string, string> Parameters { get; }
135+
protected IDictionary<string, string> Parameters { get; } =
136+
new Dictionary<string, string>(StringComparer.Ordinal);
137+
138+
/// <summary>
139+
/// Adds a parameter using the default prefix.
140+
/// </summary>
141+
/// <param name="name">The parameter name.</param>
142+
/// <param name="value">The parameter value.</param>
143+
/// <returns>The current instance, which allows chaining calls.</returns>
144+
public OpenIdAuthenticationMessage AddParameter([NotNull] string name, [CanBeNull] string value)
145+
=> AddParameter(OpenIdAuthenticationConstants.Prefixes.OpenId, name, value);
146+
147+
/// <summary>
148+
/// Adds a parameter using the specified prefix.
149+
/// </summary>
150+
/// <param name="prefix">The prefix used to discriminate the parameter.</param>
151+
/// <param name="name">The parameter to store.</param>
152+
/// <param name="value">The value associated with the parameter.</param>
153+
/// <returns>The current instance, which allows chaining calls.</returns>
154+
public OpenIdAuthenticationMessage AddParameter([NotNull] string prefix, [NotNull] string name, [CanBeNull] string value)
155+
{
156+
if (string.IsNullOrEmpty(prefix))
157+
{
158+
throw new ArgumentException("The prefix cannot be null or empty.", nameof(prefix));
159+
}
160+
161+
if (string.IsNullOrEmpty(name))
162+
{
163+
throw new ArgumentException("The parameter name cannot be null or empty.", nameof(name));
164+
}
165+
166+
if (!Parameters.ContainsKey($"{prefix}.{name}"))
167+
{
168+
Parameters.Add($"{prefix}.{name}", value);
169+
}
170+
171+
return this;
172+
}
125173

126174
/// <summary>
127175
/// Gets the attributes returned by the identity provider, or an empty
128176
/// dictionary if the message doesn't expose an attribute exchange alias.
129177
/// </summary>
130178
/// <returns>The attributes contained in this message.</returns>
131-
public IDictionary<string, string> GetAttributes()
179+
public IReadOnlyDictionary<string, string> GetAttributes()
132180
{
133181
var attributes = new Dictionary<string, string>(StringComparer.Ordinal);
134182

135-
string alias;
136-
var extensions = GetExtensions();
137183
// If the ax alias cannot be found, return an empty dictionary.
138-
if (!extensions.TryGetValue(OpenIdAuthenticationConstants.Namespaces.Ax, out alias))
184+
var extensions = GetExtensions();
185+
if (!extensions.TryGetValue(OpenIdAuthenticationConstants.Namespaces.Ax, out string alias))
139186
{
140187
return attributes;
141188
}
@@ -165,9 +212,8 @@ public IDictionary<string, string> GetAttributes()
165212
}
166213

167214
// Exclude attributes whose value is missing.
168-
string value;
169215
if (!Parameters.TryGetValue($"{OpenIdAuthenticationConstants.Prefixes.OpenId}.{alias}." +
170-
$"{OpenIdAuthenticationConstants.Suffixes.Value}.{name}", out value))
216+
$"{OpenIdAuthenticationConstants.Suffixes.Value}.{name}", out string value))
171217
{
172218
continue;
173219
}
@@ -188,7 +234,7 @@ public IDictionary<string, string> GetAttributes()
188234
/// Gets the extensions and their corresponding alias.
189235
/// </summary>
190236
/// <returns>The extensions contained in this message.</returns>
191-
public IDictionary<string, string> GetExtensions()
237+
public IReadOnlyDictionary<string, string> GetExtensions()
192238
{
193239
var extensions = new Dictionary<string, string>(StringComparer.Ordinal);
194240

@@ -212,9 +258,7 @@ public IDictionary<string, string> GetExtensions()
212258
/// <param name="name">The parameter to retrieve.</param>
213259
/// <returns>The value extracted from the parameter.</returns>
214260
public string GetParameter([NotNull] string name)
215-
{
216-
return GetParameter(OpenIdAuthenticationConstants.Prefixes.OpenId, name);
217-
}
261+
=> GetParameter(OpenIdAuthenticationConstants.Prefixes.OpenId, name);
218262

219263
/// <summary>
220264
/// Gets the parameter corresponding to the requested name and the given
@@ -235,25 +279,30 @@ public string GetParameter([NotNull] string prefix, [NotNull] string name)
235279
throw new ArgumentNullException(nameof(name));
236280
}
237281

238-
string value;
239-
if (Parameters.TryGetValue($"{prefix}.{name}", out value))
282+
if (Parameters.TryGetValue($"{prefix}.{name}", out string value))
240283
{
241284
return value;
242285
}
243286

244287
return null;
245288
}
246289

290+
/// <summary>
291+
/// Gets all the parameters associated with this instance.
292+
/// </summary>
293+
/// <returns>The parameters associated with this instance.</returns>
294+
public IReadOnlyDictionary<string, string> GetParameters()
295+
=> new ReadOnlyDictionary<string, string>(Parameters);
296+
247297
/// <summary>
248298
/// Adds, replaces or removes the parameter corresponding
249299
/// to the requested name and the default prefix.
250300
/// </summary>
251301
/// <param name="name">The parameter to store.</param>
252302
/// <param name="value">The value associated with the parameter.</param>
253-
public void SetParameter([NotNull] string name, [CanBeNull] string value)
254-
{
255-
SetParameter(OpenIdAuthenticationConstants.Prefixes.OpenId, name, value);
256-
}
303+
/// <returns>The current instance, which allows chaining calls.</returns>
304+
public OpenIdAuthenticationMessage SetParameter([NotNull] string name, [CanBeNull] string value)
305+
=> SetParameter(OpenIdAuthenticationConstants.Prefixes.OpenId, name, value);
257306

258307
/// <summary>
259308
/// Adds, replaces or removes the parameter corresponding
@@ -262,28 +311,32 @@ public void SetParameter([NotNull] string name, [CanBeNull] string value)
262311
/// <param name="prefix">The prefix used to discriminate the parameter.</param>
263312
/// <param name="name">The parameter to store.</param>
264313
/// <param name="value">The value associated with the parameter.</param>
265-
public void SetParameter([NotNull] string prefix, [NotNull] string name, [CanBeNull] string value)
314+
/// <returns>The current instance, which allows chaining calls.</returns>
315+
public OpenIdAuthenticationMessage SetParameter([NotNull] string prefix, [NotNull] string name, [CanBeNull] string value)
266316
{
267317
if (string.IsNullOrEmpty(prefix))
268318
{
269-
throw new ArgumentNullException(nameof(prefix));
319+
throw new ArgumentException("The prefix cannot be null or empty.", nameof(prefix));
270320
}
271321

272322
if (string.IsNullOrEmpty(name))
273323
{
274-
throw new ArgumentNullException(nameof(name));
324+
throw new ArgumentException("The parameter name cannot be null or empty.", nameof(name));
275325
}
276326

277327
// If the parameter value is null, remove
278328
// it from the parameters dictionary.
279329
if (string.IsNullOrEmpty(value))
280330
{
281331
Parameters.Remove($"{prefix}.{name}");
332+
}
282333

283-
return;
334+
else
335+
{
336+
Parameters[$"{prefix}.{name}"] = value;
284337
}
285338

286-
Parameters[$"{prefix}.{name}"] = value;
339+
return this;
287340
}
288341
}
289342
}

0 commit comments

Comments
 (0)