我正在尝试使用基于C#的完全自定义的Negotiate(或NTLM)实现一个简单的应用程序,它将为我作为更复杂的项目(如python中的imckaet)的基础。目前,我需要编写一个自定义的Negotiate(或NTLM)AuthenticationManager。
在Microsoft Doc中,我了解到AuthenticationManager可以做到这一点,并且在那里可以找到一个简单的CustomBasicAuthentication,但是我想实现自己的CustomNegotiate。
我实现了Authentication方法,如下所示:
public Authorization Authenticate(String challenge, WebRequest request, ICredentials credentials)
{
NetworkCredential MyCreds = credentials.GetCredential(request.RequestUri, "Ntlm");
if (PreAuthenticate(request, credentials) == null)
Console.WriteLine("\n Pre-authentication is not allowed.");
else
Console.WriteLine("\n Pre-authentication is allowed.");
bool challengeOk = checkChallenge(challenge, MyCreds.Domain);
if (!challengeOk)
return null;
// authorization.
string neg = create_NTLM_NEGOTIATE_MESSAGE(MyCreds.UserName);
HttpWebRequest req = (HttpWebRequest)WebRequest.Create(request.RequestUri);
request.ServerCertificateValidationCallback += (sender, certificate, chain, sslPolicyErrors) => true;
request.Method = "GET";
request.Headers.Add("Authorization", "Negotiate " + neg);
HttpWebResponse resp;
byte[] server_challenge = new byte[8];
try
{
resp = (HttpWebResponse)req.GetResponse();
Console.WriteLine(resp.Headers.ToString());
}
catch (WebException ex)
{
resp = ex.Response as HttpWebResponse;
string msg2 = resp.Headers["WWW-Authenticate"];
string[] challeng_string = msg2.Split(' ');
server_challenge = parse_NTLM_CHALLENGE_MESSAGE(challeng_string[1]);
}
string auth = create_NTLM_AUTHENTICATE_MESSAGE(server_challenge, MyCreds.UserName, MyCreds.Domain, MyCreds.Password);
string NtlmToken = "Negotiate " + auth;//Convert.ToBase64String(ASCII.GetBytes(BasicEncrypt));
Authorization resourceAuthorization = new Authorization(NtlmToken);
return resourceAuthorization;
}
所以我的问题是,由于“协商”作为一种挑战响应协议而起作用,并且
WebRequest请求
是如此开放,并从HttpWebRequest调用,我如何通过AuthenticationManager实现基于质询-响应的协议,以及如何通过此类发送Authorization和Authentication数据包? 如何获取质询字节以按(域\用户,密码)对生成身份验证字节?