title: WEB API 2 OAuth Client Credentials Authentication, How to add additional parameters?
body: <p>I am developing a Web API 2 with "OAuth Client Credentials" flow  where, in the first call for the authorization token, I need an additional parameter to be accessed after in the controller without the need to traffics it all the time in requests.</p>
  
  <p>What is the best way to pass an additional parameter for the authentication process and uses it later in controllers without the need for traffics it in future requests and considering security issues ?</p>
  
  <p>I found developers passing these parameters in the URL, and adding it to the OWinContext:</p>
  
  <pre><code>    public override Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
      {
  
          string clientId;
          string clientSecret;
          if (context.TryGetBasicCredentials(out clientId, out clientSecret) ||
              context.TryGetFormCredentials(out clientId, out clientSecret))
          {
              try
              {
                  if (context.Parameters.Any(x =&gt; x.Key == "Participant"))
                  {
                      // Get Participant(Additional Parameters)
                      string participant = context.Parameters.First(x =&gt; x.Key == "participant").Value[0];
  
                      //Validating Client
                      Microsoft.AspNet.Identity.PasswordHasher passwordHaser = new Microsoft.AspNet.Identity.PasswordHasher();
                      Client client = _clientAppService.GetById(Guid.Parse(clientId));
  
                      if (client != null &amp;&amp; passwordHaser.VerifyHashedPassword(client.SecretHash, clientSecret) == Microsoft.AspNet.Identity.PasswordVerificationResult.Success)
                      {
                          context.OwinContext.Set&lt;Client&gt;("oauth:client", client);
                          //Store Participant(Additional Parameters)
                          context.OwinContext.Set&lt;Participant&gt;("urn:participant", new Participant { Document = participant });
                          context.Validated();
                      }
                      else
                      {
                          context.SetError("invalid_client", "Client credentials are invalid.");
                          context.Rejected();
                      }
                  }
                  else
                  {
                      context.SetError("invalid_request", "Participant are invalid.");
                      context.Rejected();
                  }
              }
              catch (Exception)
              {
                  context.SetError("server_error");
                  context.Rejected();
              }
          }
          else
          {
              context.SetError("invalid_client", "Client credentials could not be retrieved through the Authorization header.");
              context.Rejected();
          }
  
          return Task.FromResult(0);
      }
  </code></pre>
  
  <p>And I am trying to get it via an ModelBinder, unfortunately the context always returns null:</p>
  
  <pre><code>public class ParticipantModelBinder : IModelBinder
      {
          public bool BindModel(System.Web.Http.Controllers.HttpActionContext actionContext, ModelBindingContext bindingContext)
          {
              //Returning null
              Participant participant = HttpContext.Current.GetOwinContext().Get&lt;Participant&gt;("urn:participant");
              bindingContext.Model = participant;
  
              return true;
          }
      }
  </code></pre>
  
  <p>Controller:</p>
  
  <pre><code>[Authorize]
      public class ParticipantController : ApiController
      {
          public decimal GetBalance([ModelBinder(BinderType=typeof(ParticipantModelBinder))] Participant participant)
          {
              return 0;
          }
      }
  </code></pre>
  
  <p>And another solution I found on the web is to add a new Claim on the method GrantClientCredentials, but i dont know a way to get the value on the controllers:</p>
  
  <pre><code>public override Task GrantClientCredentials(OAuthGrantClientCredentialsContext context)
      {
          //Client validated, generate token
          context.OwinContext.Response.Headers.Add("Access-Control-Allow-Origin", new[] { "*" });
          Client client = context.OwinContext.Get&lt;Client&gt;("oauth:client");
          if (client.AllowedGrant == OAuthGrant.Client)
          {
              ClaimsIdentity identity = new ClaimsIdentity(new GenericIdentity(context.ClientId, OAuthDefaults.AuthenticationType));
              identity.AddClaim(new Claim(ClaimTypes.Role, "User"));
              // Add an custum Claim with the additional parameter
              identity.AddClaim(new Claim("Participant", context.OwinContext.Get&lt;Participant&gt;("urn:participant").Document));
              context.Validated(identity);
          }
          else
          {
              context.SetError(
                  "unauthorized_client",
                  "The authenticated client is not authorized to use this authorization grant type");
          }
  
          return Task.FromResult(0);
      }
  </code></pre>