I need to find all the groups a particular user is a member of. I'm using C++, not Powershell, if this is the wrong forum I apologize.
From what I've found on the web I need to retrieve the memberOf property, but I keep getting an error that the property doesn't exist. Any help would be appreciated. Here's the code:
HRESULT hrObj = E_FAIL; HRESULT hr = E_FAIL; ADS_SEARCHPREF_INFO SearchPrefs; // COL for iterations ADS_SEARCH_COLUMN col; // Handle used for searching ADS_SEARCH_HANDLE hSearch;
// Set attributes to return. LPWSTR pszAttribute[NUM_ATTRIBUTES] = {L"ADsPath"};
// Execute the search. hr = pSearchBase->ExecuteSearch(pszSearchFilter, pszAttribute, NUM_ATTRIBUTES, &hSearch); if (SUCCEEDED(hr)) { // Call IDirectorySearch::GetNextRow() to retrieve the next row of data. while(pSearchBase->GetNextRow(hSearch) != S_ADS_NOMORE_ROWS) { // Loop through the array of passed column names and // print the data for each column. for (DWORD x = 0; x < NUM_ATTRIBUTES; x++) { // Get the data for this column. hr = pSearchBase->GetColumn(hSearch, pszAttribute[x], &col); if (SUCCEEDED(hr)) { // Print the data for the column and free the column. // Be aware that the requested attribute is type CaseIgnoreString. if (ADSTYPE_CASE_IGNORE_STRING == col.dwADsType) { IADs *pADS; hr = ADsOpenObject( col.pADsValues->CaseIgnoreString, L"Administrator", L"passW0rd", ADS_SECURE_AUTHENTICATION, IID_IADs, (void**)&pADS);
If the user does not belong to any groups you will get an error trying to access the memberof property. Are you certain the user you are doing the search for belongs to some groups?
If you're on .NET 3.5 or up, you can use the new System.DirectoryServices.AccountManagement(S.DS.AM) namespace which makes this a lot easier than it used to be.
// find your user UserPrincipal user =UserPrincipal.FindByIdentity(yourDomain, userName);
// if found - grab its groups if(user !=null) { PrincipalSearchResult<Principal> groups = user.GetAuthorizationGroups();
// iterate over all groups foreach(Principal p in groups) { // make sure to add only group principals if(p isGroupPrincipal) { result.Add((GroupPrincipal)p); } } }
return result; }
and that's all there is! You now have a result (a list) of authorization groups that user belongs to - iterate over them, print out their names or whatever you need to do.
Hope it helps ou.
Thank you
Lepide Softwares
Lepide Softwares Pvt. Ltd.
http://www.lepide.com/
products:
Lepide Exchange Manager,
Lepide Active Directory Self Service,
Lepide Active Directory Management and reporting,
Mail id: anilk@lepide.com
contact no: 1-800-814-0578
Thanks, I have to do it in C++. I'll do some research to see if there is a C++ equivalent for what you suggested, or if I can call that managed code from C++. Thanks gain.
None
0 Points
5 Posts
Need to retrieve all groups a user belongs to...
May 04, 2012 10:08 AM|funkycold|LINK
Hi,
I need to find all the groups a particular user is a member of. I'm using C++, not Powershell, if this is the wrong forum I apologize.
From what I've found on the web I need to retrieve the memberOf property, but I keep getting an error that the property doesn't exist. Any help would be appreciated. Here's the code:
HRESULT hrObj = E_FAIL;
HRESULT hr = E_FAIL;
ADS_SEARCHPREF_INFO SearchPrefs;
// COL for iterations
ADS_SEARCH_COLUMN col;
// Handle used for searching
ADS_SEARCH_HANDLE hSearch;
// Search entire subtree from root.
SearchPrefs.dwSearchPref = ADS_SEARCHPREF_SEARCH_SCOPE;
SearchPrefs.vValue.dwType = ADSTYPE_INTEGER;
SearchPrefs.vValue.Integer = ADS_SCOPE_SUBTREE;
// Set the search preference.
DWORD dwNumPrefs = 1;
hr = pSearchBase->SetSearchPreference(&SearchPrefs, dwNumPrefs);
if (FAILED(hr))
{
return hr;
}
// Create search filter.
LPWSTR pszFormat = L"(&(objectCategory=person)(objectClass=user)(sAMAccountName=%s))";
int len = wcslen(pszFormat) + wcslen(szFindUser) + 1;
LPWSTR pszSearchFilter = new WCHAR[len];
if(NULL == pszSearchFilter)
{
return E_OUTOFMEMORY;
}
swprintf_s(pszSearchFilter, len, pszFormat, szFindUser);
// Set attributes to return.
LPWSTR pszAttribute[NUM_ATTRIBUTES] = {L"ADsPath"};
// Execute the search.
hr = pSearchBase->ExecuteSearch(pszSearchFilter,
pszAttribute,
NUM_ATTRIBUTES,
&hSearch);
if (SUCCEEDED(hr))
{
// Call IDirectorySearch::GetNextRow() to retrieve the next row of data.
while(pSearchBase->GetNextRow(hSearch) != S_ADS_NOMORE_ROWS)
{
// Loop through the array of passed column names and
// print the data for each column.
for (DWORD x = 0; x < NUM_ATTRIBUTES; x++)
{
// Get the data for this column.
hr = pSearchBase->GetColumn(hSearch, pszAttribute[x], &col);
if (SUCCEEDED(hr))
{
// Print the data for the column and free the column.
// Be aware that the requested attribute is type CaseIgnoreString.
if (ADSTYPE_CASE_IGNORE_STRING == col.dwADsType)
{
IADs *pADS;
hr = ADsOpenObject( col.pADsValues->CaseIgnoreString,
L"Administrator",
L"passW0rd",
ADS_SECURE_AUTHENTICATION,
IID_IADs,
(void**)&pADS);
VARIANT var;
VariantInit(&var);
if (SUCCEEDED(hr))
{
hr = pADS->GetEx(L"memberOf", &var); <-- FAILS!!!
wprintf(L"Found User.\n",szFindUser);
wprintf(L"%s: %s\r\n",pszAttribute[x],col.pADsValues->CaseIgnoreString);
hrObj = S_OK;
}
}
pSearchBase->FreeColumn( &col );
}
else
{
hr = E_FAIL;
}
}
}
// Close the search handle to cleanup.
pSearchBase->CloseSearchHandle(hSearch);
}
delete pszSearchFilter;
if (FAILED(hrObj))
{
hr = hrObj;
}
Participant
1062 Points
428 Posts
Re: Need to retrieve all groups a user belongs to...
May 04, 2012 03:49 PM|gww|LINK
If the user does not belong to any groups you will get an error trying to access the memberof property. Are you certain the user you are doing the search for belongs to some groups?
Member
20 Points
4 Posts
Re: Need to retrieve all groups a user belongs to...
May 07, 2012 06:12 AM|voodooclanboy|LINK
If you're on .NET 3.5 or up, you can use the new
System.DirectoryServices.AccountManagement
(S.DS.AM) namespace which makes this a lot easier than it used to be.Read all about it here: Managing Directory Security Principals in the .NET Framework 3.5
Basically, you need to have a "principal context" (typically your domain), a user principal, and then you get its groups very easily:
and that's all there is! You now have a result (a list) of authorization groups that user belongs to - iterate over them, print out their names or whatever you need to do.
http://www.lepide.com/
products:
Lepide Exchange Manager,
Lepide Active Directory Self Service,
Lepide Active Directory Management and reporting,
Mail id: anilk@lepide.com
contact no: 1-800-814-0578
None
0 Points
5 Posts
Re: Need to retrieve all groups a user belongs to...
May 07, 2012 07:28 AM|funkycold|LINK
gww, yes, the user is in a group called Users.
None
0 Points
5 Posts
Re: Need to retrieve all groups a user belongs to...
May 07, 2012 07:32 AM|funkycold|LINK
voodooclanboy,
Thanks, I have to do it in C++. I'll do some research to see if there is a C++ equivalent for what you suggested, or if I can call that managed code from C++. Thanks gain.
None
0 Points
5 Posts
Re: Need to retrieve all groups a user belongs to...
May 07, 2012 08:34 AM|funkycold|LINK
Thanks for all the replies, I think I just found what I needed in MSDN:
HRESULT CheckUserGroups(IADsUser *pUser)
{
IADsMembers *pGroups;
HRESULT hr = S_OK;
hr = pUser->Groups(&pGroups);
pUser->Release();
if (FAILED(hr)) return hr;
IUnknown *pUnk;
hr = pGroups->get__NewEnum(&pUnk);
if (FAILED(hr)) return hr;
pGroups->Release();
IEnumVARIANT *pEnum;
hr = pUnk->QueryInterface(IID_IEnumVARIANT,(void**)&pEnum);
if (FAILED(hr)) return hr;
pUnk->Release();
// Enumerate.
BSTR bstr;
VARIANT var;
IADs *pADs;
ULONG lFetch;
IDispatch *pDisp;
VariantInit(&var);
hr = pEnum->Next(1, &var, &lFetch);
while(hr == S_OK)
{
if (lFetch == 1)
{
pDisp = V_DISPATCH(&var);
pDisp->QueryInterface(IID_IADs, (void**)&pADs);
pADs->get_Name(&bstr);
printf("Group belonged: %S\n",bstr);
SysFreeString(bstr);
pADs->Release();
}
VariantClear(&var);
pDisp=NULL;
hr = pEnum->Next(1, &var, &lFetch);
};
hr = pEnum->Release();
return S_OK;
}