Exemple de code pour la détection des collisions de noms de schéma
Cette rubrique contient un exemple de code qui détecte les collisions de noms de schéma.
L’exemple de code C/C++ suivant interroge le schéma pour obtenir les attributs de nom de clé sur un objet classSchema ou attributeSchema .
Elle retourne la valeur true si des attributs ou des classes en conflit sont trouvés. Elle retourne false si l’attribut ou la classe avec le CN, lDAPDisplayName, OID, schemaIDGUID ou LinkId spécifié n’est pas en conflit avec le schéma et, par conséquent, peut être ajouté en toute sécurité au schéma.
/********************************************************************
FindCollidingAttributesOrClasses()
********************************************************************/
HRESULT FindCollidingAttributesOrClasses(
IDirectorySearch *pSchemaNC, // IDirectorySearch pointer to
// schema naming context.
LPWSTR szName,
LPWSTR szLDAPDisplayName,
LPWSTR szOID,
const GUID * pSchemaIDGUID,
DWORD dwLinkID, // Value is zero (0) if the attribute is not linked,
// or if checking for class.
BOOL *pfIsColliding)
{
if (!pSchemaNC ||
!szName ||
!szLDAPDisplayName ||
!szOID ||
!pSchemaIDGUID)
{
return E_POINTER;
}
HRESULT hr = E_FAIL;
LPWSTR szBuffer = NULL;
hr = ADsEncodeBinaryData((LPBYTE)pSchemaIDGUID,
sizeof(GUID),
&szBuffer);
if (SUCCEEDED(hr))
{
LPWSTR pwszFormatLinkID = L"(|(cn=%s)(lDAPDisplayName=%s)(attributeID=%s)(governsID=%s)(schemaIDGUID=%s)(linkID=%d))";
LPWSTR pwszFormatNoLinkID = L"(|(cn=%s)(lDAPDisplayName=%s)(attributeID=%s)(governsID=%s)(schemaIDGUID=%s))";
LPWSTR szFilter = new WCHAR[lstrlenW(pwszFormatLinkID) +
lstrlenW(szName) +
lstrlenW(szLDAPDisplayName) +
lstrlenW(szOID) +
lstrlenW(szOID) +
lstrlenW(szBuffer) +
20 +
1];
if(szFilter)
{
if (dwLinkID > 0L)
{
swprintf_s(szFilter,
pwszFormatLinkID,
szName,
szLDAPDisplayName,
szOID,
szOID,
szBuffer,
dwLinkID);
}
else
{
swprintf_s(szFilter,
pwszFormatNoLinkID,
szName,
szLDAPDisplayName,
szOID,
szOID,
szBuffer);
}
// Attributes are one-level deep in the Schema
// container so only search one level.
ADS_SEARCHPREF_INFO SearchPrefs[2];
SearchPrefs[0].dwSearchPref = ADS_SEARCHPREF_SEARCH_SCOPE;
SearchPrefs[0].vValue.dwType = ADSTYPE_INTEGER;
SearchPrefs[0].vValue.Integer = ADS_SCOPE_ONELEVEL;
SearchPrefs[1].dwSearchPref = ADS_SEARCHPREF_PAGESIZE;
SearchPrefs[1].vValue.dwType = ADSTYPE_INTEGER;
SearchPrefs[1].vValue.Integer = 1000;
int iCount = 0;
// Set the search preference
hr = pSchemaNC->SetSearchPreference(
SearchPrefs,
sizeof(SearchPrefs)/sizeof(ADS_SEARCHPREF_INFO)
);
if (SUCCEEDED(hr))
{
LPWSTR pszAttribs[] = {
L"lDAPDisplayName",
L"cn",
L"attributeID",
L"governsID",
L"schemaIDGUID",
L"linkID",
L"objectCategory"
};
// Handle used for searching
ADS_SEARCH_HANDLE hSearch = NULL;
DWORD x = 0L;
hr = pSchemaNC->ExecuteSearch(szFilter,
pszAttribs,
sizeof(pszAttribs)/sizeof(LPWSTR),
&hSearch);
if (SUCCEEDED(hr))
{
// Call IDirectorySearch::GetNextRow()
// to retrieve the next row of data.
hr = pSchemaNC->GetFirstRow(hSearch);
while (hr != S_ADS_NOMORE_ROWS)
{
// Keep track of count.
iCount++;
// Get the next row
hr = pSchemaNC->GetNextRow(hSearch);
}
// Close the search handle to cleanup
pSchemaNC->CloseSearchHandle(hSearch);
if(SUCCEEDED(hr))
{
if (0 == iCount)
{
*pfIsColliding = FALSE;
}
else
{
*pfIsColliding = TRUE;
}
hr = S_OK;
}
}
}
delete szFilter;
}
FreeADsMem(szBuffer);
}
return hr;
}