2017-08-11 151 views
1

我有一个www.api.com和一个www.client.com 所有注册都将在api.com完成,登录将在api.com完成。 client.com只能看到登录表单的用户界面。来自客户端的web api认证

用户登录后,api.com将令牌返回给用户。如何使用令牌访问api.com中其余的webapi?我想访问GetExployeeByID方法。使用后登录。我保存在该单词在sessionStorage.setItem('token', data.access_token)

API方法

[RoutePrefix("api/Customer")] 
public class CustomerController : ApiController 
{ 
    List<customer> list = new List<customer>() { new customer {id=1 ,customerName="Marry",age=13}, 
     new customer { id = 2, customerName = "John", age = 24 } }; 

    [Route("GetExployeeByID/{id:long}")] 
    [HttpGet] 
    [Authorize] 
    public customer GetExployeeByID(long id) 
    {  
     return list.FirstOrDefault(x=>x.id==id); 
    } 

} 

更新1 这是我的AJAX后调用API登录后

function lgetemp() { 
    $.ajax({ 
     url: 'http://www.azapi.com:81/api/customer/GetExployeeByID/1', 
     datatype:"json", 
     type: 'get', 
     headers: { 
      "access_token":sessionStorage.getItem("token") 
     }, 
     crossDomain: true, 
     success: function (data) { 
      debugger 
      alert(data.customerName) 
     }, 
     error: function (err) { 
      debugger 
      alert('error') 
     } 

    }) 
} 

回答

0

您应该通过令牌在从客户端到api的请求的头部中

Authorization Basic yJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY= 

从API可以查询标题并取出令牌。

string authorizationHeader = HttpContext.Current.Request.Headers["Authorization"]; 
string toke = authorizationHeader.Replace("Bearer ", String.Empty); 

我已经在我的最新项目做什么是有一个类AuthToken,做了很多这对我来说

public class AuthToken : IAuthToken 
{ 
    private string _raw; 
    private IDictionary<string, string> _deserialized; 

    public string Raw 
    { 
     get 
     { 
      if (String.IsNullOrWhiteSpace(_raw)) 
      { 
       string authorizationHeader = HttpContext.Current.Request.Headers["Authorization"]; 
       _raw = authorizationHeader.Replace("Bearer ", String.Empty); 
      } 
      return _raw; 
     } 
    } 

    public IDictionary<string, string> Deserialized 
    { 
     get 
     { 
      if (_deserialized == null) 
      { 
       string[] tokenSplit = Raw.Split('.'); 
       string payload = tokenSplit[1]; 
       byte[] payloadBytes = Convert.FromBase64String(payload); 
       string payloadDecoded = Encoding.UTF8.GetString(payloadBytes); 
       _deserialized = JsonConvert.DeserializeObject<IDictionary<string, string>>(payloadDecoded); 
      } 
      return _deserialized; 
     } 
    } 
} 

然后我注入的是为UserContext类,我可以注入我的控制器等。用户上下文然后可以根据需要从令牌中提取声明。 (假设它是JWT)

public class UserContext : IUserContext 
{ 
    private IList<Claim> _claims; 
    private string _identifier; 
    private string _email; 
    private string _clientId; 

    public IAuthToken Token { get; } 

    public IList<Claim> Claims 
    { 
     get 
     { 
      return _claims ?? (_claims = Token.Deserialized.Select(self => new Claim(self.Key, self.Value)).ToList()); 
     } 
    } 

    public string Identifier => _identifier ?? (_identifier = Token.Deserialized.ContainsKey("sub") ? Token.Deserialized["sub"] : null); 

    public string Email => _email ?? (_email = Token.Deserialized.ContainsKey(ClaimTypes.Email) ? Token.Deserialized[ClaimTypes.Email] : null); 

    public UserContext(IAuthToken authToken) 
    { 
     Token = authToken; 
    } 
} 
+0

将令牌传递回api后。如何对它进行修改?microsft是否为此构建了代码? –

+1

我的朋友是另外一个问题! :-) –

+0

,因为我已经在标题中传递了令牌。我不知道该往哪里继续。也许我的问题标题有些误导 –

0

您需要将令牌传递给请求标头并调用API url。通过传递您拥有的URL和令牌可以调用以下函数。

static string CallApi(string url, string token) 
{ 
    ServicePointManager.ServerCertificateValidationCallback += (sender, cert, chain, sslPolicyErrors) => true; 
    using (var client = new HttpClient()) 
    { 
     if (!string.IsNullOrWhiteSpace(token)) 
     { 
      var t = JsonConvert.DeserializeObject<Token>(token); 

      client.DefaultRequestHeaders.Clear(); 
      client.DefaultRequestHeaders.Add("Authorization", "Bearer " + t.access_token); 
     } 
     var response = client.GetAsync(url).Result; 
     return response.Content.ReadAsStringAsync().Result; 
    } 
} 

请参阅 - Token based authentication in Web API的详细说明。