2015-03-03 4 views
1

Я перемещаю некоторые общие атрибуты в отдельный проект vs, так что я могу легко использовать их в нескольких проектах. Одним из атрибутов для контроллеров WebAPI и обеспечивает запрос с использованием протокола HTTPS:Атрибуты во внешних сборках

public class EnsureHttpsAttribute : ActionFilterAttribute 
{ 
    public override void OnActionExecuting(HttpActionContext actionContext) 
    { 
     if(actionContext == null) 
     { 
      throw new ArgumentNullException("actionContext"); 
     } 

     if(actionContext.Request.RequestUri.Scheme != Uri.UriSchemeHttps) 
     { 
      HandleNonHttpsRequest(actionContext); 
     } 
    } 

    protected virtual HttpResponseMessage HandleNonHttpsRequest(HttpActionContext actionContext) 
    { 
     HttpResponseMessage response = null; 

     if(actionContext.Request.Method.Equals(HttpMethod.Get) || actionContext.Request.Method.Equals(HttpMethod.Head)) 
     { 
      UriBuilder newUrlBuilder = new UriBuilder(actionContext.Request.RequestUri); 
      newUrlBuilder.Scheme = Uri.UriSchemeHttps; 
      newUrlBuilder.Port = 443; 

      response = actionContext.Request.CreateResponse(HttpStatusCode.Found); 

      response.Headers.Location = newUrlBuilder.Uri; 
     } 
     else 
     { 
      response = actionContext.Request.CreateResponse(HttpStatusCode.NotFound); 
     } 

     actionContext.Response = response; 

     return response; 
    } 

    public System.Threading.Tasks.Task<HttpResponseMessage> ExecuteAuthorizationFilterAsync(HttpActionContext actionContext, System.Threading.CancellationToken cancellationToken, Func<System.Threading.Tasks.Task<HttpResponseMessage>> continuation) 
    { 
     if(actionContext == null) 
     { 
      throw new ArgumentNullException("actionContext"); 
     } 

     if(actionContext.Request.RequestUri.Scheme != Uri.UriSchemeHttps) 
     { 
      return Task.FromResult<HttpResponseMessage>(HandleNonHttpsRequest(actionContext)); 
     } 
     else 
     { 
      return continuation(); 
     } 
    } 
} 

Я затем добавить атрибут следующим образом:

config.Filters.Add(new EnsureHttpsAttribute()); 

Проблема заключается в том, что, когда атрибут является ссылка от отдельного проекта, он не вызван. Проект компилируется и запускается без проблем - кроме того, что атрибут не выполняется. Если я переведу атрибут в тот же проект webapi, атрибут будет выполнен. У меня есть другие атрибуты, которые используют утверждения для авторизации запроса - они не выполняются ни при части отдельного проекта.

Неужели кто-нибудь испытал это раньше?

+0

Работает как очарование для меня, вы уверены, что используете одну и ту же версию System.Web.Http и System.Net.Http в обоих проектах? –

+0

@JosVinke Спасибо за ответ. Я создал новый веб-проект api и попытался использовать отдельный проект - он работал, как ожидалось. Я заметил, что как в этом новом проекте, так и в оригинале было несоответствие версии System.Web.Http (4.0.0.0 и 5.2.3.0) - я обновил проекты, чтобы они все потребляли 5.2.3.0 и теперь все работает. Вы знаете, почему это может вызвать проблемы? Я бы ожидал исключения. – markpirvine

+0

Хорошо, что сейчас он работает, но я не знаю, в чем причина этой проблемы. Существует значительная разница между реализацией ActionFilterAttribute из версий 4.0.0.0 и 5.2.3.0 (например, добавлением методов Async), но я не уверен, что причиной этой проблемы может быть также некоторое изменение в конвейере HTTP. Если вы это выясните, сообщите мне. –

ответ

0

Должно быть возможно поместить ваши атрибуты в внешний проект.

Пожалуйста, убедитесь, что вы используете один и тот же System.Web.Http и System.Net.Http версии в обоих проектах.

Смежные вопросы