Active Directory issues using IIS7 in Windows Server 2008 R2 - iis-7

The web app I'm working on uses both User ID's and Group ID's from Active Directory. That is, users can inherit access to some parts of the app (specifically reports) based on their membership in AD Groups.
So, we're using the User's GUID and Group's GUID as a key in the database tracking access to features.
App is working fine in development environment (IIS7 running on Windows 7). But when I try to set the site up in my test environment (IIS7 running on Windows Server 2008 R2), I get the following error:
Unable to cast object of type 'System.DirectoryServices.AccountManagement.GroupPrincipal' to type 'System.DirectoryServices.AccountManagement.UserPrincipal'.
From the stack trace, it appears that the guilty code is:
public string UserGUID
{
get
{
return UserPrincipal.Current.Guid.ToString();
}
}
I'm also accessing GroupPrincipals in a method that fetches all the groups a specific User belongs to:
public ArrayList Get_UserGroupGUIDs(string username)
{
ArrayList oList = new ArrayList();
// "company" is the domain we would like to search in
using ( PrincipalContext ctx = new PrincipalContext ( ContextType.Domain, "isidc.com" ) )
{
// get the user of that domain by his username, within the context
using ( UserPrincipal up = UserPrincipal.FindByIdentity(ctx, IdentityType.SamAccountName, username))
{
if (up != null)
{
// fetch the group list
using (PrincipalSearchResult<Principal> Groups = up.GetAuthorizationGroups())
{
foreach (GroupPrincipal g in Groups)
{
oList.Add(g.Guid.ToString());
} // end foreach
} // end using
} // end if
} // end using
return oList;
} // end method Get_UserGroupGUIDs
Any ideas?

Related

Asp MVC IIS User permission

I use this code in my application to display some images stored on a network drive, for example with the path //MyCompanyServer/Folder
public ActionResult DocumentoLista(string area)
{
if (String.IsNullOrEmpty(area))
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
var doc = db.Documentos.Where(x => x.area == area).FirstOrDefault();
if (doc == null)
{
return HttpNotFound();
}
string dirPath = Path.GetFullPath(doc.path);
List<string> dirs = new List<string>(Directory.EnumerateDirectories(dirPath));
List<string> files = new List<string>();
DirectoryInfo dirInfo = new DirectoryInfo(dirPath);
foreach (string fInfo in Directory.EnumerateFiles(dirPath, "*.*", SearchOption.TopDirectoryOnly)
.Where(s => s.EndsWith(".png")
|| s.EndsWith(".PNG")
|| s.EndsWith(".jpg")
|| s.EndsWith(".JPG")
).Select(Path.GetFileName)
)
{
files.Add(fInfo);
}
ViewBag.Area = area;
ViewBag.Dirs = dirs;
ViewBag.MyList = files;
return View(doc);
}
It works perfectly on my dev machine but when I tried it from my deployment server, it doesn´t work. I think that maybe it´s not working because in my dev computer I´m executing it with my LDAP user and in my production server (IIS) the user is different and it doesn´t have permision to access to this path.
¿Could be?
Witch user executes asp applications? to what user do I need to give permissions in order to make it work?
Thanks
Pretty sure that the user your application pool is running under doesn't have permissions for that path, you need to:
Locate your application pool in IIS
Check the user account it's running against (In Basic Settings)
Give that user access to the path that you're trying to access (using windows security).
Give IUSR access to the folder.
http://www.iis.net/learn/get-started/planning-for-security/understanding-built-in-user-and-group-accounts-in-iis

System.DirectoryServices.AccountManagement PrincipalContext impersonation to create new user

In Sharepoint (or any ASP.NET web application) I want to have a function to create AD users. I'm using System.DirectoryServices.AccountManagement for this task, but I'm getting into trouble. Here is my code:
using (var pc = new PrincipalContext(ContextType.Domain,"DOMAIN","administrator","password"))
{
if (pc.ValidateCredentials("administrator", "password"))
{
UserPrincipal up = new UserPrincipal(pc, username, password, true);
up.Save();
}
}
The user gets created but it is disabled. I know that my administrator:password pair is correct because "if" statement is returning true. Also during creation I receive Exception:
Exception has been thrown by the target of an invocation.
I checked PrincipalContext object and it is connecting to domain controller with "administrator" account. What could be the reason of this error and up.Save() function throwing Exception ?
Can you try the following:
using (var pc = new PrincipalContext(ContextType.Domain,"DOMAIN","administrator","password"))
{
using (var up = new UserPrincipal(pc))
{
up.SamAccountName = textboxUsername.Text; // Username
up.SetPassword(textboxPassword.Text); // Password
up.Enabled = true;
up.ExpirePasswordNow();
up.Save();
}
}
This should at least make sure that the user is created and is enabled. Let me know if it works.

Wrong entries in webpages_Roles table

I have created a standard ASP.NET MVC project in VS12 using the "Internet Application" Template for Web Applications.
VS has automatically created a database called aspnet-Authentification-20130123105949.mdf. When I open the database table webpages_Roles just one of my created Roles is shown there. But this role doesn't exist anymore, it seems as if the data shown here is old.
I add roles by using:
public String AddRole(String name)
{
Roles.CreateRole(name);
return name + " was added.";
}
My method to list the roles shows different roles than in the DB view:
public String ListRoles()
{
String[] roles = Roles.GetAllRoles();
String res = "";
foreach(String role in roles) {
res += "\n" + role;
}
return res;
}
I've already tried to refresh the DB View, but this does not help.
I have no problems with other databases created by myself.

How to get user details in asp.net Windows Authentication

I am using windows Authentication and accessing user name as.
IIdentity winId = HttpContext.Current.User.Identity;
string name = winId.Name;
but i want to get other details like User full name and EmailID.
Since you're on a windows network, then you need to query the Active directory to search for user and then get it's properties such as the email
Here is an example function DisplayUser that given an IIdentity on a windows authenticated network, finds the user's email:
public static void Main() {
DisplayUser(WindowsIdentity.GetCurrent());
Console.ReadKey();
}
public static void DisplayUser(IIdentity id) {
WindowsIdentity winId = id as WindowsIdentity;
if (id == null) {
Console.WriteLine("Identity is not a windows identity");
return;
}
string userInQuestion = winId.Name.Split('\\')[1];
string myDomain = winId.Name.Split('\\')[0]; // this is the domain that the user is in
// the account that this program runs in should be authenticated in there
DirectoryEntry entry = new DirectoryEntry("LDAP://" + myDomain);
DirectorySearcher adSearcher = new DirectorySearcher(entry);
adSearcher.SearchScope = SearchScope.Subtree;
adSearcher.Filter = "(&(objectClass=user)(samaccountname=" + userInQuestion + "))";
SearchResult userObject = adSearcher.FindOne();
if (userObject != null) {
string[] props = new string[] { "title", "mail" };
foreach (string prop in props) {
Console.WriteLine("{0} : {1}", prop, userObject.Properties[prop][0]);
}
}
}
gives this:
Edit: If you get 'bad user/password errors'
The account that the code runs under must have access the users domain. If you run code in asp.net then the web application must be run under an application pool with credentials with domain access. See here for more information
You can define a MyCustomIdentity by overriding from IIdentity and add your own properties etc.
Cast it to the specific Identity, for example WindowsIdentity

How to list Windows users and groups in ASP.NET?

I have a ASP.NET Website project and I need to list all the users and their groups on my Windows system. I have set the identity impersonation to true and provided the username and password of the admin in the web.config. Where do I start?
Thanks in advance.
Update:
I have the following code at the moment -
var machine = new DirectoryEntry("WinNT://<IP ADDRESS>");
foreach (DirectoryEntry child in machine.Children)
{
// get the child's group(s).
}
When I debug, I can see the list of users in machine.Children. How do I find the group(s) that this user belongs to?
This article covers how to talk to Active Directory and should get you where you want to go:
http://www.codeproject.com/KB/system/everythingInAD.aspx
To get users, you would do something like this:
public List<string> GetUserList()
{
string DomainName="";
string ADUsername="";
string ADPassword="";
List<string> list=new List<string>();
DirectoryEntry entry=new DirectoryEntry(LDAPConnectionString, ADUsername, ADPassword);
DirectorySearcher dSearch=new DirectorySearcher(entry);
dSearch.Filter="(&(objectClass=user))";
foreach(SearchResult sResultSet in dSearch.FindAll())
{
string str=GetProperty(sResultSet, "userPrincipalName");
if(str!="")
list.Add(str);
}
return list;
}
You probably want to start with the DirectoryEntry and Active Directory support in .net.
Here's a good resource: http://www.codeproject.com/KB/system/everythingInAD.aspx
Local access is similar, even if you're not in a domain:
DirectoryEntry localMachine = new DirectoryEntry("WinNT://" +
Environment.MachineName);
DirectoryEntry admGroup = localMachine.Children.Find("administrators",
"group");
object members = admGroup.Invoke("members", null);
foreach (object groupMember in (IEnumerable)members) {
DirectoryEntry member = new DirectoryEntry(groupMember);
//...
}

Resources