React to Http changes

This commit is contained in:
Hao Kung 2015-06-25 17:10:13 -07:00
parent 38f70a02f7
commit 7b31e034ca
4 changed files with 34 additions and 40 deletions

View File

@ -43,14 +43,14 @@ namespace Microsoft.AspNet.Server.WebListener
_customChallenges = AuthenticationSchemes.None; _customChallenges = AuthenticationSchemes.None;
} }
public void Authenticate(AuthenticateContext context) public Task AuthenticateAsync(AuthenticateContext context)
{ {
var user = _requestContext.User; var user = _requestContext.User;
var identity = user == null ? null : (ClaimsIdentity)user.Identity; var identity = user == null ? null : (ClaimsIdentity)user.Identity;
foreach (var authType in ListEnabledAuthSchemes()) foreach (var authType in ListEnabledAuthSchemes())
{ {
string authScheme = authType.ToString(); var authScheme = authType.ToString();
if (string.Equals(authScheme, context.AuthenticationScheme, StringComparison.Ordinal)) if (string.Equals(authScheme, context.AuthenticationScheme, StringComparison.Ordinal))
{ {
if (identity != null && identity.IsAuthenticated if (identity != null && identity.IsAuthenticated
@ -64,29 +64,26 @@ namespace Microsoft.AspNet.Server.WebListener
} }
} }
} }
}
public Task AuthenticateAsync(AuthenticateContext context)
{
Authenticate(context);
return Task.FromResult(0); return Task.FromResult(0);
} }
public void Challenge(ChallengeContext context) public Task ChallengeAsync(ChallengeContext context)
{ {
foreach (var scheme in ListEnabledAuthSchemes()) foreach (var scheme in ListEnabledAuthSchemes())
{ {
var authScheme = scheme.ToString(); var authScheme = scheme.ToString();
// Not including any auth types means it's a blanket challenge for any auth type. // Not including any auth types means it's a blanket challenge for any auth type.
if (context.AuthenticationScheme == null || if (context.AuthenticationScheme == string.Empty ||
string.Equals(context.AuthenticationScheme, authScheme, StringComparison.Ordinal)) string.Equals(context.AuthenticationScheme, authScheme, StringComparison.Ordinal))
{ {
_requestContext.Response.StatusCode = 401;
_customChallenges |= scheme; _customChallenges |= scheme;
context.Accept(); context.Accept();
} }
} }
// A challenge was issued, it overrides any pre-set auth types. // A challenge was issued, it overrides any pre-set auth types.
_requestContext.AuthenticationChallenges = _customChallenges; _requestContext.AuthenticationChallenges = _customChallenges;
return Task.FromResult(0);
} }
public void GetDescriptions(DescribeSchemesContext context) public void GetDescriptions(DescribeSchemesContext context)
@ -98,14 +95,16 @@ namespace Microsoft.AspNet.Server.WebListener
} }
} }
public void SignIn(SignInContext context) public Task SignInAsync(SignInContext context)
{ {
// Not supported // Not supported
return Task.FromResult(0);
} }
public void SignOut(SignOutContext context) public Task SignOutAsync(SignOutContext context)
{ {
// Not supported // Not supported
return Task.FromResult(0);
} }
private IDictionary<string, object> GetDescription(string authenticationScheme) private IDictionary<string, object> GetDescription(string authenticationScheme)

View File

@ -47,7 +47,7 @@ namespace Microsoft.AspNet.Server.WebListener
IHttpUpgradeFeature, IHttpUpgradeFeature,
IHttpRequestIdentifierFeature IHttpRequestIdentifierFeature
{ {
private static Action<object> OnStartDelegate = OnStart; private static Func<object,Task> OnStartDelegate = OnStart;
private RequestContext _requestContext; private RequestContext _requestContext;
private FeatureCollection _features; private FeatureCollection _features;
@ -378,12 +378,12 @@ namespace Microsoft.AspNet.Server.WebListener
get { return Response.HasStarted; } get { return Response.HasStarted; }
} }
void IHttpResponseFeature.OnResponseStarting(Action<object> callback, object state) void IHttpResponseFeature.OnResponseStarting(Func<object, Task> callback, object state)
{ {
Response.OnResponseStarting(callback, state); Response.OnResponseStarting(callback, state);
} }
void IHttpResponseFeature.OnResponseCompleted(Action<object> callback, object state) void IHttpResponseFeature.OnResponseCompleted(Func<object, Task> callback, object state)
{ {
Response.OnResponseCompleted(callback, state); Response.OnResponseCompleted(callback, state);
} }
@ -484,11 +484,12 @@ namespace Microsoft.AspNet.Server.WebListener
set { _requestId = value; } set { _requestId = value; }
} }
private static void OnStart(object obj) private static Task OnStart(object obj)
{ {
var featureContext = (FeatureContext)obj; var featureContext = (FeatureContext)obj;
ConsiderEnablingResponseCache(featureContext); ConsiderEnablingResponseCache(featureContext);
return Task.FromResult(0);
} }
private static void ConsiderEnablingResponseCache(FeatureContext featureContext) private static void ConsiderEnablingResponseCache(FeatureContext featureContext)

View File

@ -48,8 +48,8 @@ namespace Microsoft.Net.Http.Server
private long _expectedBodyLength; private long _expectedBodyLength;
private BoundaryType _boundaryType; private BoundaryType _boundaryType;
private HttpApi.HTTP_RESPONSE_V2 _nativeResponse; private HttpApi.HTTP_RESPONSE_V2 _nativeResponse;
private IList<Tuple<Action<object>, object>> _onResponseStartingActions; private IList<Tuple<Func<object, Task>, object>> _onResponseStartingActions;
private IList<Tuple<Action<object>, object>> _onResponseCompletedActions; private IList<Tuple<Func<object, Task>, object>> _onResponseCompletedActions;
private RequestContext _requestContext; private RequestContext _requestContext;
private bool _bufferingEnabled; private bool _bufferingEnabled;
@ -80,8 +80,8 @@ namespace Microsoft.Net.Http.Server
_nativeResponse.Response_V1.Version.MajorVersion = 1; _nativeResponse.Response_V1.Version.MajorVersion = 1;
_nativeResponse.Response_V1.Version.MinorVersion = 1; _nativeResponse.Response_V1.Version.MinorVersion = 1;
_responseState = ResponseState.Created; _responseState = ResponseState.Created;
_onResponseStartingActions = new List<Tuple<Action<object>, object>>(); _onResponseStartingActions = new List<Tuple<Func<object, Task>, object>>();
_onResponseCompletedActions = new List<Tuple<Action<object>, object>>(); _onResponseCompletedActions = new List<Tuple<Func<object, Task>, object>>();
_bufferingEnabled = _requestContext.Server.BufferResponses; _bufferingEnabled = _requestContext.Server.BufferResponses;
_expectedBodyLength = 0; _expectedBodyLength = 0;
_nativeStream = null; _nativeStream = null;
@ -773,18 +773,18 @@ namespace Microsoft.Net.Http.Server
_nativeStream.SwitchToOpaqueMode(); _nativeStream.SwitchToOpaqueMode();
} }
public void OnResponseStarting(Action<object> callback, object state) public void OnResponseStarting(Func<object, Task> callback, object state)
{ {
IList<Tuple<Action<object>, object>> actions = _onResponseStartingActions; var actions = _onResponseStartingActions;
if (actions == null) if (actions == null)
{ {
throw new InvalidOperationException("Response already started"); throw new InvalidOperationException("Response already started");
} }
actions.Add(new Tuple<Action<object>, object>(callback, state)); actions.Add(new Tuple<Func<object, Task>, object>(callback, state));
} }
public void OnResponseCompleted(Action<object> callback, object state) public void OnResponseCompleted(Func<object, Task> callback, object state)
{ {
var actions = _onResponseCompletedActions; var actions = _onResponseCompletedActions;
if (actions == null) if (actions == null)
@ -792,7 +792,7 @@ namespace Microsoft.Net.Http.Server
throw new InvalidOperationException("Response already completed"); throw new InvalidOperationException("Response already completed");
} }
actions.Add(new Tuple<Action<object>, object>(callback, state)); actions.Add(new Tuple<Func<object, Task>, object>(callback, state));
} }
private void NotifyOnSendingHeaders() private void NotifyOnSendingHeaders()

View File

@ -256,17 +256,16 @@ namespace Microsoft.AspNet.Server.WebListener
{ {
string address; string address;
var authTypeList = authType.ToString().Split(new char[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries); var authTypeList = authType.ToString().Split(new char[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries);
using (Utilities.CreateHttpAuthServer(authType | AuthenticationSchemes.AllowAnonymous, out address, env => using (Utilities.CreateHttpAuthServer(authType | AuthenticationSchemes.AllowAnonymous, out address, async env =>
{ {
var context = new DefaultHttpContext((IFeatureCollection)env); var context = new DefaultHttpContext((IFeatureCollection)env);
Assert.NotNull(context.User); Assert.NotNull(context.User);
Assert.False(context.User.Identity.IsAuthenticated); Assert.False(context.User.Identity.IsAuthenticated);
foreach (var scheme in authTypeList) foreach (var scheme in authTypeList)
{ {
var authResults = context.Authentication.Authenticate(scheme); var authResults = await context.Authentication.AuthenticateAsync(scheme);
Assert.Null(authResults); Assert.Null(authResults);
} }
return Task.FromResult(0);
})) }))
{ {
var response = await SendRequestAsync(address); var response = await SendRequestAsync(address);
@ -286,7 +285,7 @@ namespace Microsoft.AspNet.Server.WebListener
{ {
string address; string address;
var authTypeList = authType.ToString().Split(new char[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries); var authTypeList = authType.ToString().Split(new char[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries);
using (Utilities.CreateHttpAuthServer(authType, out address, env => using (Utilities.CreateHttpAuthServer(authType, out address, async env =>
{ {
var context = new DefaultHttpContext((IFeatureCollection)env); var context = new DefaultHttpContext((IFeatureCollection)env);
Assert.NotNull(context.User); Assert.NotNull(context.User);
@ -294,14 +293,13 @@ namespace Microsoft.AspNet.Server.WebListener
var count = 0; var count = 0;
foreach (var scheme in authTypeList) foreach (var scheme in authTypeList)
{ {
var authResults = context.Authentication.Authenticate(scheme); var authResults = await context.Authentication.AuthenticateAsync(scheme);
if (authResults != null) if (authResults != null)
{ {
count++; count++;
} }
} }
Assert.Equal(1, count); Assert.Equal(1, count);
return Task.FromResult(0);
})) }))
{ {
var response = await SendRequestAsync(address, useDefaultCredentials: true); var response = await SendRequestAsync(address, useDefaultCredentials: true);
@ -325,8 +323,7 @@ namespace Microsoft.AspNet.Server.WebListener
var context = new DefaultHttpContext((IFeatureCollection)env); var context = new DefaultHttpContext((IFeatureCollection)env);
Assert.NotNull(context.User); Assert.NotNull(context.User);
Assert.False(context.User.Identity.IsAuthenticated); Assert.False(context.User.Identity.IsAuthenticated);
context.Authentication.Challenge(); return context.Authentication.ChallengeAsync();
return Task.FromResult(0);
})) }))
{ {
var response = await SendRequestAsync(address); var response = await SendRequestAsync(address);
@ -346,16 +343,15 @@ namespace Microsoft.AspNet.Server.WebListener
{ {
string address; string address;
var authTypeList = authType.ToString().Split(new char[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries); var authTypeList = authType.ToString().Split(new char[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries);
using (Utilities.CreateHttpAuthServer(authType | AuthenticationSchemes.AllowAnonymous, out address, env => using (Utilities.CreateHttpAuthServer(authType | AuthenticationSchemes.AllowAnonymous, out address, async env =>
{ {
var context = new DefaultHttpContext((IFeatureCollection)env); var context = new DefaultHttpContext((IFeatureCollection)env);
Assert.NotNull(context.User); Assert.NotNull(context.User);
Assert.False(context.User.Identity.IsAuthenticated); Assert.False(context.User.Identity.IsAuthenticated);
foreach (var scheme in authTypeList) foreach (var scheme in authTypeList)
{ {
context.Authentication.Challenge(scheme); await context.Authentication.ChallengeAsync(scheme);
} }
return Task.FromResult(0);
})) }))
{ {
var response = await SendRequestAsync(address); var response = await SendRequestAsync(address);
@ -379,8 +375,7 @@ namespace Microsoft.AspNet.Server.WebListener
var context = new DefaultHttpContext((IFeatureCollection)env); var context = new DefaultHttpContext((IFeatureCollection)env);
Assert.NotNull(context.User); Assert.NotNull(context.User);
Assert.False(context.User.Identity.IsAuthenticated); Assert.False(context.User.Identity.IsAuthenticated);
context.Authentication.Challenge(authType.ToString()); return context.Authentication.ChallengeAsync(authType.ToString());
return Task.FromResult(0);
})) }))
{ {
var response = await SendRequestAsync(address); var response = await SendRequestAsync(address);
@ -407,12 +402,11 @@ namespace Microsoft.AspNet.Server.WebListener
var context = new DefaultHttpContext((IFeatureCollection)env); var context = new DefaultHttpContext((IFeatureCollection)env);
Assert.NotNull(context.User); Assert.NotNull(context.User);
Assert.False(context.User.Identity.IsAuthenticated); Assert.False(context.User.Identity.IsAuthenticated);
Assert.Throws<InvalidOperationException>(() => context.Authentication.Challenge(authType.ToString())); return Assert.ThrowsAsync<InvalidOperationException>(() => context.Authentication.ChallengeAsync(authType.ToString()));
return Task.FromResult(0);
})) }))
{ {
var response = await SendRequestAsync(address); var response = await SendRequestAsync(address);
Assert.Equal(HttpStatusCode.Unauthorized, response.StatusCode); Assert.Equal(HttpStatusCode.OK, response.StatusCode);
Assert.Equal(0, response.Headers.WwwAuthenticate.Count); Assert.Equal(0, response.Headers.WwwAuthenticate.Count);
} }
} }