Share via


Esecuzione di una query di ambito attributo

La query dell'ambito dell'attributo è una preferenza di ricerca che consente l'esecuzione di una ricerca degli attributi con valori di nome distinti di un oggetto. L'attributo da cercare può essere singolo o multivalore, ma deve essere del tipo ADS_DN_STRING . Quando viene eseguita la ricerca, ADSI enumererà i valori dei nomi distinti dell'attributo ed eseguirà la ricerca sugli oggetti rappresentati dai nomi distinti. Ad esempio, se viene eseguita una ricerca con ambito attributo dell'attributo membro di un oggetto gruppo, ADSI enumererà i nomi distinti nell'attributo membro e cercherà ognuno dei membri del gruppo per i criteri di ricerca specificati.

Se viene eseguita una query con ambito attributo su un attributo che non è di tipo ADS_DN_STRING, la ricerca avrà esito negativo. La query con ambito attributo richiede anche che la preferenza ADS_edizione StandardARCHPREF_edizione StandardARCH_SCOPE sia impostata su ADS_SCOPE_BAedizione Standard. La preferenza ADS_edizione StandardARCHPREF_edizione StandardARCH_SCOPE verrà impostata automaticamente su ADS_SCOPE_BAedizione Standard, ma se la preferenza ADS_edizione StandardARCHPREF_edizione StandardARCH_SCOPE è impostata su qualsiasi altro valore, IDirectorySearch::SetSearchPreference avrà esito negativo con E_ADS_BAD_PARAMETER.

I risultati di una query con ambito di attributo possono estendersi su più server e un server potrebbe non restituire tutti i dati richiesti per tutte le righe restituite. In questo caso, quando l'ultima riga viene recuperata chiamando IDirectorySearch::GetNextRow o IDirectorySearch::GetFirstRow, ADSI restituirà S_ADS_ERRORSOCCURRED anziché S_ADS_NOMORE_ROWS.

Per specificare una query dell'ambito dell'attributo, impostare un'opzione di ricerca ADS_edizione StandardARCHPREF_ATTRIBUTE_QUERY con un valore ADSTYPE_CAedizione Standard_IGNORE_STRING impostato su lDAPDisplayName dell'attributo da cercare nella matrice ADS_edizione StandardARCHPREF_INFO passata a IDirectorySearch::SetSearchPreference Metodo. Questa operazione è illustrata nell'esempio di codice seguente.

ADS_SEARCHPREF_INFO SearchPref;
SearchPref.dwSearchPref = ADS_SEARCHPREF_ATTRIBUTE_QUERY;
SearchPref.vValue.dwType = ADSTYPE_CASE_IGNORE_STRING;
SearchPref.vValue.Boolean = L"member";

Nell'esempio di codice seguente viene illustrato come usare l'opzione di ricerca ADS_edizione StandardARCHPREF_ATTRIBUTE_QUERY.

/***************************************************************************

    SearchGroupMembers()

    Searches the members of a group that are of type user and prints each 
    user's cn and distinguishedName values to the console.

    Parameters:

    pwszGroupDN - Contains the distinguished name of the group whose 
    members will be searched.

***************************************************************************/

HRESULT SearchGroupMembers(LPCWSTR pwszGroupDN)
{
    HRESULT hr;
    CComPtr<IDirectorySearch> spSearch;
    CComBSTR sbstrADsPath;
 
    // Bind to the group and get the IDirectorySearch interface.
    sbstrADsPath = "LDAP://";
    sbstrADsPath += pwszGroupDN;
    hr = ADsOpenObject(sbstrADsPath,
        NULL,
        NULL,
        ADS_SECURE_AUTHENTICATION,
        IID_IDirectorySearch,
        (void**)&spSearch);
    if(FAILED(hr))
    {
        return hr;
    }
 
    ADS_SEARCHPREF_INFO SearchPrefs[1];

    // Set the ADS_SEARCHPREF_ATTRIBUTE_QUERY search preference.
    SearchPrefs[0].dwSearchPref = ADS_SEARCHPREF_ATTRIBUTE_QUERY;
    SearchPrefs[0].vValue.dwType = ADSTYPE_CASE_IGNORE_STRING;
    SearchPrefs[0].vValue.CaseIgnoreString = L"member";

    // Set the search preferences.
    hr = spSearch->SetSearchPreference(SearchPrefs, sizeof(SearchPrefs)/sizeof(ADS_SEARCHPREF_INFO));
    if(FAILED(hr))
    {
        return hr;
    }

    ADS_SEARCH_HANDLE hSearch;
    
    // Create the search filter.
    LPWSTR pwszSearchFilter = L"(&(objectClass=user))";
 
    // Set attributes to return.
    LPWSTR rgpwszAttributes[] = {L"cn", L"distinguishedName"};
    DWORD dwNumAttributes = sizeof(rgpwszAttributes)/sizeof(LPWSTR);
 
    // Execute the search.
    hr = spSearch->ExecuteSearch(pwszSearchFilter,
        rgpwszAttributes,
        dwNumAttributes,
        &hSearch);
    if(FAILED(hr))
    {
        return hr;
    }

    // Get the first result row.
    hr = spSearch->GetFirstRow(hSearch);
    while(S_OK == hr)
    {
        ADS_SEARCH_COLUMN col;

        // Enumerate the retrieved attributes.
        for(DWORD i = 0; i < dwNumAttributes; i++)
        {
            hr = spSearch->GetColumn(hSearch, rgpwszAttributes[i], &col);
            if(SUCCEEDED(hr))
            {
                switch(col.dwADsType)
                {
                case ADSTYPE_DN_STRING:
                    wprintf(L"%s: %s\n\n", rgpwszAttributes[i], col.pADsValues[0].DNString);
                    break;

                case ADSTYPE_CASE_IGNORE_STRING:
                    wprintf(L"%s: %s\n\n", rgpwszAttributes[i], col.pADsValues[0].CaseExactString);
                    break;

                default:
                    break;
                }
                
                // Free the column.
                spSearch->FreeColumn(&col);
            }
        }
        
        // Get the next row.
        hr = spSearch->GetNextRow(hSearch);
    }

    // Close the search handle to cleanup.
    hr = spSearch->CloseSearchHandle(hSearch);

    return hr;
}

Quando questa ricerca viene eseguita e i risultati vengono enumerati, restituisce il nome, il numero di telefono e il numero di ufficio di tutti gli oggetti utente contenuti nell'elenco di attributi membro del gruppo.

Gestione degli errori: i risultati di una query con ambito di attributo possono estendersi su più server e un server potrebbe non restituire tutti i dati richiesti per tutte le righe restituite. In questo caso, quando l'ultima riga viene recuperata chiamando GetNextRow o GetFirstRow, ADSI restituirà S_ADS_ERRORSOCCURRED anziché S_ADS_NOMORE_ROWS.