【发布时间】:2011-10-15 23:00:25
【问题描述】:
我们有一个 Forms Authenticated Intranet,它向 AD 查询登录信息并将 Windows 身份的副本存储在会话中,以便以后在更新其 AD 条目时模拟用户。我们不能使用 Windows 身份验证来模拟(长话短说)。
所以登录代码是:
[DllImport("advapi32.dll")]
public static extern bool LogonUser(String
lpszUsername, String lpszDomain,
String lpszPassword, int dwLogonType, int
dwLogonProvider, out int phToken);
public bool LoginWindowsUser(String domain, String username, String pwd, HttpSessionStateBase session)
{
int ret = 0;
int l_token1;
bool loggedOn = LogonUser(username,
domain, pwd,
// Logon type=LOGON32_LOGON_NETWORK_CLEARTEXT.
3,
// Logon provider=LOGON32_PROVIDER_DEFAULT.
0,
// User token for specified user is returned
//here.
out l_token1);
if (loggedOn)
{
IntPtr token2 = new IntPtr(l_token1);
var l_Wid = new WindowsIdentity(token2);
session["WindowsIdentity"] = l_Wid;
}
return loggedOn;
}
然后当我们需要更新用户的广告信息时,我们会这样做:
public void UpdateUserProperty(string username, string propertyName, string propertyValue)
{
// Obtain the authenticated user's identity.
var winId = (WindowsIdentity) ControllerContext.HttpContext.Session["WindowsIdentity"];
// Start impersonating.
using (WindowsImpersonationContext ctx = winId.Impersonate())
{
try
{
var ds = new DirectorySearcher();
int ind = username.IndexOf("\\") + 1;
username = username.Substring(ind, username.Length - ind);
var filter = "(&(objectCategory=Person)(objectClass=user)";
if (!username.IsNullOrEmpty())
{
filter += "(samaccountname=*{0}*)".F(username);
}
filter += ")";
ds.Filter = filter;
foreach (var property in ADUserDetailsDisplay.LoadProperties())
{
ds.PropertiesToLoad.Add(property);
}
///////////// ERROR OCCURS AFTER NEXT LINE /////////////
var searchResult = ds.FindOne();
var userDirectoryEntry = searchResult.GetDirectoryEntry();
if (propertyValue.IsNullOrEmpty())
{
if (userDirectoryEntry.Properties[propertyName].Count > 0) userDirectoryEntry.Properties[propertyName].RemoveAt(0);
}
else if (userDirectoryEntry.Properties[propertyName].Count == 0)
{
userDirectoryEntry.Properties[propertyName].Add(propertyValue);
}
else
{
userDirectoryEntry.Properties[propertyName][0] = propertyValue;
}
userDirectoryEntry.CommitChanges();
}
catch (Exception ex)
{
TempData.AddErrorMessage("Unable to update user: " + ex.Message);
}
finally
{
// Revert impersonation.
if (ctx != null)
ctx.Undo();
}
}
// Back to running under the default ASP.NET process identity.
}
问题是我们收到以下错误:
无法更新用户:出现操作错误。
如果有人能指导我找到解决方案,我将不胜感激。
使用 IIS 7.5 Win2008 R2 ASP.NET MVC2
谢谢。
【问题讨论】:
标签: c# asp.net active-directory impersonation