15/11/2024

Active Directory

Active Directory – PowerShell : récupérer la liste des utilisateurs de plusieurs OU

I. Présentation

La flexibilité de PowerShell s'avère très pratique lorsqu'il s'agit d'interroger un annuaire Active Directory. Notamment si l'on souhaite récupérer la liste des utilisateurs (ou d'un autre type d'objets) au sein de plusieurs OU, sans prendre tout l'annuaire.

Grâce à un script PowerShell simple, nous allons pouvoir générer facilement cette liste d'utilisateurs sans passer par des exports multiples dans la console Active Directory, qu'il faudra ensuite fusionner... Bref, pas pratique.

II. Le script

La première étape consiste à définir un tableau qui va servir à lister les OU pour lesquelles nous souhaitons récupérer les utilisateurs. Dans la variable $OUList sera stocké le tableau. Par exemple, pour 4 OU différentes, cela donne :

$OUList = @("OU=Comptabilite,DC=it-connect,DC=local", 
            "OU=Secretariat,DC=it-connect,DC=local", 
            "OU=Direction,DC=it-connect,DC=local", 
            "OU=Commercial,DC=it-connect,DC=local")

La suite est simple : pour chaque OU du tableau, nous allons récupérer la liste des utilisateurs grâce à Get-ADUser qui sera utilisé avec le paramètre SearchBase qui aura notre OU comme valeur. Ainsi, on récupère que les utilisateurs de l'OU, et cela pour nos 4 OU. Dans cet exemple, je sélectionne uniquement le SamAccountName mais vous pouvez ajouter d'autres propriétés.

Ce qui donne le script complet suivant :

$OUList = @("OU=Comptabilite,DC=it-connect,DC=local",
            "OU=Secretariat,DC=it-connect,DC=local",
            "OU=Direction,DC=it-connect,DC=local",
            "OU=Commercial,DC=it-connect,DC=local")

$Users = Foreach($OU in $OUList){

    Get-ADUser -Filter * -SearchBase $OU | Select-Object SamAccountName

}

$Users | Export-CSV -Path "C:\Users.csv" -NoTypeInformation

La variable $Users contient tous les utilisateurs, nous pouvons facilement l'exporter vers un fichier CSV grâce au cmdlet Export-CSV comme vous pouvez le voir sur la dernière ligne du script ci-dessus.

Voilà, simple mais efficace, non ? ?

author avatar
Florian BURNEL Co-founder of IT-Connect
Ingénieur système et réseau, cofondateur d'IT-Connect et Microsoft MVP "Cloud and Datacenter Management". Je souhaite partager mon expérience et mes découvertes au travers de mes articles. Généraliste avec une attirance particulière pour les solutions Microsoft et le scripting. Bonne lecture.
Partagez cet article Partager sur Twitter Partager sur Facebook Partager sur Linkedin Envoyer par mail

33 commentaires sur “Active Directory – PowerShell : récupérer la liste des utilisateurs de plusieurs OU

  • Bonjour,
    merci pour le tuto, par contre si je veux récupérer le nom du compte ainsi que l’utilisateur à coté quel commande je dois rajouter ? J’ai essayé de rajouter la ligne :
    Get-ADUser -Filter * -SearchBase $OU | Select-Object distinguishedName
    en dessous de :
    Get-ADUser -Filter * -SearchBase $OU | Select-Object SamAccountName

    mais ça ne fonctionne pas.
    Merci de m’aider 🙂

    Répondre
    • Bonjour Guillaume,

      Il vaut mieux utiliser directement cette syntaxe :

      Get-ADUser -Filter * -SearchBase $OU | Select-Object SamAccountName, distinguishedName

      Fait un essai et redis-moi 🙂
      Florian

      Répondre
  • Bonjour Florian,

    Comme Guillaume, je cherche à avoir un peu plus d’informations sur l’utilisateur, comme son nom, son mail, et sa date de dernière connexion.

    Sais tu ou je peux trouver le nom des champs que je dois ajouter derrière le Select-Object.

    Merci pour ton aide,

    Répondre
  • Bon, ben je viens de trouver la solution à mon problème.

    Voici les champs accessibles :

    AccountExpirationDate :
    accountExpires :
    AccountLockoutTime :
    AccountNotDelegated :
    AllowReversiblePasswordEncryption :
    AuthenticationPolicy : {}
    AuthenticationPolicySilo : {}
    BadLogonCount : 0
    badPwdCount : 0
    CannotChangePassword :
    CanonicalName :
    Certificates : {}
    City :
    CN :
    co :
    codePage :
    Company :
    CompoundIdentitySupported : {}
    Country :
    countryCode :
    Created :
    createTimeStamp :
    Deleted :
    Department :
    Description :
    DisplayName :
    DistinguishedName :
    Division :
    DoesNotRequirePreAuth :
    dSCorePropagationData : {}
    EmailAddress :
    EmployeeID :
    EmployeeNumber :
    Enabled :
    extensionAttribute10 :
    extensionAttribute12 :
    extensionAttribute13 :
    extensionAttribute14 :
    extensionAttribute15 :
    Fax :
    GivenName :
    HomeDirectory :
    HomedirRequired :
    HomeDrive :
    HomePage :
    HomePhone :
    Initials :
    instanceType :
    isDeleted :
    KerberosEncryptionType : {}
    l :
    LastBadPasswordAttempt :
    LastKnownParent :
    LastLogonDate :
    lastLogonTimestamp :
    LockedOut :
    lockoutTime :
    LogonWorkstations :
    mail :
    mailNickname :
    Manager :
    MemberOf : {}
    MNSLogonAccount :
    MobilePhone :
    Modified :
    modifyTimeStamp :
    mS-DS-ConsistencyGuid :
    msDS-User-Account-Control-Computed :
    Name :
    nTSecurityDescriptor :
    ObjectCategory :
    ObjectClass :
    ObjectGUID :
    objectSid :
    Office :
    OfficePhone :
    Organization :
    OtherName :
    PasswordExpired :
    PasswordLastSet :
    PasswordNeverExpires :
    PasswordNotRequired :
    personalTitle :
    physicalDeliveryOfficeName :
    POBox :
    PostalCode :
    PrimaryGroup :
    primaryGroupID :
    PrincipalsAllowedToDelegateToAccount : {}
    ProfilePath :
    ProtectedFromAccidentalDeletion :
    proxyAddresses : {}
    pwdLastSet :
    SamAccountName :
    sAMAccountType :
    ScriptPath :
    sDRightsEffective :
    ServicePrincipalNames : {}
    SID :
    SIDHistory :
    SmartcardLogonRequired :
    sn :
    State :
    StreetAddress :
    Surname :
    targetAddress :
    Title :
    TrustedForDelegation :
    TrustedToAuthForDelegation :
    UseDESKeyOnly :
    userAccountControl :
    userCertificate :
    UserPrincipalName :
    uSNChanged :
    uSNCreated :
    whenChanged :
    whenCreated :

    Si cela peut servir à quelqu’un …

    Répondre
    • Bonjour William,

      Oui effectivement il s’agit de la liste des attributs. Pour les utiliser dans le script, il faut ajouter l’option « -Properties » et indiquer derrière les noms des attributs à « charger » car par défaut il y en a seulement quelques-uns d’affiché.

      Bonne journée
      Florian

      Répondre
  • Bonjour,

    Est-il possible de lister directement les users de l’OU et de ses sous-OU ?

    Merci 🙂

    Répondre
    • Bonjour Nico,
      La commande actuelle prend directement en compte les sous-OU pour chaque OU définie dans la liste ?
      Redis moi si tu as un problème.
      Cordialement,
      Florian

      Répondre
      • J’ai dans chaque OU d’autres OU qui contiennent elles-mêmes d’autres OU, etc.
        Ce que je souhaiterais c’est exporter tous les utilisateurs de OU et de ses sous OU sans avoir à les spécifier dans le script sinon je vais mettre des plombes a faire le script ^^

        Répondre
        • Si tu as une OU de haut niveau qui contient toutes les sous OU que tu veux cibler, tu n’as qu’à l’indiquer et ce sera récursif pour récupérer les utilisateurs dans les sous-OU (à partir de cette racine).

          Répondre
          • Bonjour
            C’est exactement ce que j’ai fait, et ça fonctionne très bien! Merci.
            Par contre je voudrais exclure quelques sous OU, connais tu un moyen de le faire?
            Soit je liste chaque sous OU (long et surtout penser à modifier le script en cas d’ajout)
            soit je prend l’OU racine et ai trop de resultats
            Merci pour ton aide

            Répondre
            • Hello Cynthia,
              Je ne sais pas si tu as trouvé une réponse à ta question.
              En tout cas, voici un exemple pour exclure l’OU « OU=Support-IT,OU=Personnel,DC=it-connect,DC=local » (il suffit d’ajouter une condition -OR pour en mettre plusieurs) mais le « * » peut t’aider aussi.

              Get-ADUser -Filter * -SearchBase 'OU=Personnel,DC=it-connect,DC=local' |
              Where-Object { $_.DistinguishedName -notlike '*OU=Support-IT,OU=Personnel,*' } |
              Select-Object SamAccountName

              En espérant que cela puisse t’aider ! 🙂
              A+
              Florian

              Répondre
  • Bonjour Florian,

    Merci pour tout et bonne et heureuse annee.

    Et t’il possible de faire la recherche directement a partir d’un domaine card dans mon cas j’ai plusieur domaines
    Ce qui donnerait quelque chose comme ca:

    $DList = @(« DC=we,DC=local,DC=net »,
    « DC=ee,DC=local »,DC=net »,
    « DC=na,DC=local »,DC=net »,
    « DC=la,DC=local »,DC=net »)
    Ensuite je voudrais avoir comme resultat tous les users qui ont des compte sur plusieur domaine.
    Je pourrai faire une boucle qui prendari chaque user et verifirai si le user existe sure un autre domaine mais je ne trouve pas ca tres « propre » car si un user a pluseur compte le script va faire le meme traivaille plusieur fois.
    Et je ne vois pas comment faire autrement 🙁

    Merci pour ton aide.

    Répondre
    • Bonjour Eric,

      Merci, bonne année également 🙂
      Si les domaines sont membres de la même forêt, ce qui semble être le cas d’après l’exemple, cela me semble possible.
      Tu peux stocker la liste de l’ensemble des utilisateurs dans la variable $Users et ensuite créer une variable qui va contenir tous les comptes une seule fois (à toi de définir l’attribut sur lequel se baser). Il restera à comparer la variable $Users avec la variable qui contient qu’une fois chaque utilisateur ($UsersUnique) pour faire ressortir ceux qui sont présents deux fois. Trois lignes utiles pour éclaircir mes propos :

      $Users += (Get-ADUser -Filter * -SearchBase "" | Select-Object SamAccountName).SamAccountName
      $UsersUnique = $Users | Select-Object -Unique
      Compare-object -ReferenceObject $UsersUnique -DifferenceObject $Users

      Si ce n’est pas clair, dis moi 🙂
      Cordialement,
      Florian

      Répondre
      • Bonjour Florian,

        Merci de ton aide.
        J’ai essaye ton code en rajoutant un pipe cvs

        Compare-object -ReferenceObject $UsersUnique -DifferenceObject $Users | Export -cvs – path $path -NoTypeInformation -Encoding UTF8

        Mais je me retrouve avec la liste complete des utilisateurs et pas simplement les duplicates

        J’ai essaye le meme en changeant la derniere ligne

        $users | Group-Object -Property userprincipalname | where-object -property count -gt 2 | Export-Csv -Path $path -Encoding UTF8 -Delimiter « ; » -NoTypeInformation

        Le resultat dans le fichier est le suivant
        Values count Group name
        System.collections.arrayList 55 **

        **System.Collections.ObjectModel.Collection’1[System.Management.Automation.PSObject]

        Je ne comprends pas pourquoi je n’est pas la liste des UPNs dans le fichier 🙁

        Répondre
  • Bonjour Florian,

    Je vais essaye d’etre plus clair
    Voici mon code

    #Je recupere mes differnts domaines we,ee,it,la…
    $Alldomains = (Get-ADForest).domains

    #Affecte une valeur a ma variable path
    $path = « c:\users.csv »

    #J’initialise mon tableau users
    $users=@()

    # je fais une boucle qui va me recuperer dans ma variable users tous les UPN des tous mes usrs sous tous mes domaines
    foreach ($domain in $Alldomains)
    {
    $users+=get-aduser -Filter * -Server $domain | select UserPrincipalName
    }

    #la je pense que ca va pas **
    $users | Group-Object UserPrincipalName | select name,count | Export-Csv -Path $path -Encoding UTF8 -Delimiter « ; » -NoTypeInformation

    ** Le Group-Object UserPrincipalName ne fait « rien » en tout cas je ne voit pas trop ce qu’il fais pour la raison suivante
    chaque users de mon tableau a un unique UPN
    [email protected]
    [email protected]

    J’ai donc en sorti la liste de tous les users commen par example [email protected] ; 1

    meme chose avec
    $users | Group-Object -Property userprincipalname | where-object -property count -gt 2 | Export-Csv -Path $path -Encoding UTF8 -Delimiter « ; » -NoTypeInformation

    Il faudrait que je fasse un trie en fonction du prenom et du nom et ensuite en sorti L’UPN complet pour voir sous quel domain le user a un compte.

    Répondre
    • Bonjour Eric,

      Pour être sûr de bien comprendre, pourrais-tu me dire sur quel attribut tu veux te baser pour détecter les doublons ? Ensuite je vois pour faire quelques tests.

      Cordialement,
      Florian

      Répondre
  • Bonjour Florian
    J’ai une préoccupation.
    quel script peut inventorier les utilisateurs locaux des postes de travail contenu dans l’AD et sur les serveurs

    merci

    Répondre
  • Salut et merci pour ce script,
    J’essaye d’ajouter le displayname et le mail au script, mais les colonnes restes vides
    voici la ligne

    Get-ADUser -Filter * -SearchBase $OU | Select-Object SamAccountName,displayName,mail

    tu parles de properties mais je ne sais pas ou ajouter l’option

    Bonjour William,

    Oui effectivement il s’agit de la liste des attributs. Pour les utiliser dans le script, il faut ajouter l’option « -Properties » et indiquer derrière les noms des attributs à « charger » car par défaut il y en a seulement quelques-uns d’affiché.

    Bonne journée
    Florian

    Répondre
    • Hello akalinski,

      Essaie avec cette commande :

      Get-ADUser -Filter * -SearchBase $OU -Properties DisplayName,Mail | Select-Object SamAccountName,displayName,mail

      C’est mieux ? 🙂

      Bon courage
      Florian

      Répondre
  • Bonjour et déjà merci pour votre travail.

    Débutant en powershell, je recherche une commande ou un bout de script permettant de :

    -lister les utilisateurs avec date de création et de dernière connexion de mon AD sur ma VM

    Sur un de vos précédent tuto, je me suis basé sur la récupération des utilisateurs, ajoutés dans l’AD depuis J-1.

    L’idée est de pouvoir récupérer les nouveaux entrant dans l’AD , comme un scan journalier dans l’AD et que le script exporte les résultats (seulement s’il y a changement et de manière autonome) sous forme de fichier CSV.

    Merci de votre retour,
    en espérant avoir été à peu prêt claire ^^

    Répondre
  • Bonjour Florian

    Un immense merci pour la qualité de tes cours.
    J’ai besoin de tes lumières et de ton aide. J’ai créé u script afin de rapatrié mes utilisateurs dans une liste déroulante. Jusque la tout va bien sauf que dans ma liste les utilisateurs apparaissent sous la forme par exemple @{Name=Henri DUPOND}. Comment puis faire pour supprimer @{Name= } et n’avoir que Henri DUPOND.
    Merci de ton aide
    Eric

    Répondre
  • Bonjour,
    Merci pour votre script qui m’a bien aidé comme je suis un moins que débutant en Powershell.
    Je recherche la possibilité d’ajouter dans la boucle des utilisateurs trouvés de récupérer chaque groupe auquel chacun a accès.
    Merci d’avance
    Francois

    Répondre
  • Pour illustrer ma demande :

    Liste des OU à vérifier …

    Boucle de chaque utilisateur trouvé
    Boucle pour avoir l’appartenance aux Groupes
    Affichage de l’OU, du nom et tous les groupes
    fin boucle Groupes
    Fin boucle utilisateurs

    Exportation en csv des éléments affichés dans la dernière boucle.

    Ma demande est surement plus explicite comme cela 🙂

    Merci de votre aide

    Répondre
  • Pour compléter ma demande :

    liste des OU a vérifier

    boucle de recherche des utilisateurs de la liste des OU à vérifier
    boucle de recherche d’appartenance aux différents groupes pour chaque utilisateur
    affichage du nom de l’utilisateur, de l’OU d’appartenance, nom du groupe d’appartenance
    fin de boucle des groupes d’appartenance
    fin de la boucle des utilisateurs

    Exportation au format Excel des toutes les données affichées

    J’espère que ma demande est désormais un peu plus claire. 🙂

    Merci pour votre aide

    Répondre
  • Le script qui m’affiche bien les utilisateurs mais pas les groupes auxquels ils appartiennent individuellement :

    $OUList = @(« OU=… »,
    « OU=… »,
    « OU=… »)
    $Users = Foreach($OU in $OUList)
    {
    Get-ADUser -Filter * -SearchBase $OU | Select-Object Name
    $Groupes = Foreach($Nom in $Users)
    {
    # Get-ADGroupMember $($Group.Name)
    (GET-ADUSER –Identity $Nom –Properties MemberOf | Select-Object MemberOf).MemberOf
    }
    }
    $Users | Export-CSV -Path « C:\Temp\Users.csv » -NoTypeInformation
    $Groupes | Export-CSV -Path « C:\Temp\Groupes.csv » -NoTypeInformation

    Merci de votre aide

    Répondre
    • Hello,

      Voici un bout de code qui devrait vous aider (et vous plaire) :

      $OUList = @("OU=Personnel,DC=it-connect,DC=local")
      $CSV = Foreach($OU in $OUList)
      {
      $UsersList = Get-ADUser -Filter * -SearchBase $OU | Select-Object SamAccountName, DistinguishedName
      Foreach($User in $UsersList){
      Write-Host "Traitement de $($User.SamAccountName) ($($User.DistinguishedName))" -ForegroundColor Green
      $UserName = $User.SamAccountName
      $UserDN = $User.DistinguishedName
      $GroupOfThisUser = @((Get-ADPrincipalGroupMembership -Identity $User.SamAccountName).Name) -join ','
      [PSCustomObject]@{
      Utilisateurs = $UserName
      Emplacement = $UserDN
      Groupes = $GroupOfThisUser
      }
      }
      }
      $CSV | Export-CSV -Path "C:\users.csv" -Delimiter ";" -NoTypeInformation

      A+
      Florian

      Répondre
  • Bonjour Florian,
    Parfait comme script. Je devrais m’en sortir maintenant.
    Avec tous mes remerciements.
    Francois

    Répondre
  • Super merci !
    À noter que si on récupère d’autres champs (nom / prénom dans mon cas) qui contiennent des accents, il faut spécifier l’encodage UTF8 à Export-CSV :
    $Users | Export-CSV -Path « C:\chemin.csv » -NoTypeInformation -Encoding UTF8

    Répondre
  • Bonjour,
    Selon les heures, le script fonctionnait parfaitement ou me renvoyait une erreur (comme ci-dessous). Mais maintenant, je n’arrive plus à trouver (au hasard) un créneau horaire qui me permette de le faire fonctionner.
    J’ai toujours l’erreur suivante :
    ———————————————————————————————————————-
    Traitement de CN=francois.daideone,OU=Utilisateurs,OU=NOM_OU,DC=FR
    Get-ADPrincipalGroupMembership : L’opération demandée n’a pas été effectuée car l’utilisateur n’a pas été authentifié
    Au caractère Ligne:17 : 31
    + … isUser = @((Get-ADPrincipalGroupMembership -Identity $User.SamAccount …
    + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo : NotSpecified: (f.daideone:ADPrincipal) [Get-ADPrincipalGroupMembership], ADException
    + FullyQualifiedErrorId : ActiveDirectoryServer:1244,Microsoft.ActiveDirectory.Management.Commands.GetADPrincipalGroupMembership
    ———————————————————————————————————————-
    Ce petit (mais néanmoins génial) script m’aide énormément et maintenant que j’y ai gouté, je ne saurais revenir en arrière.
    Merci de votre aide

    Répondre
  • Bonjour
    je chercherais a extraire les membres de dossier contenu dans l’onglet securite
    « noms de groupes ou et utilisateurs  »
    pourriez-vous m’aider ?
    j’avoue ne pas trop savoir comment obtenir sa par powershell
    merci

    Répondre
  • Bonjour Florian merci pour ce code. J’ai une demande svp. Avec mon script j’ai récupéré des utilisateurs depuis un fichier csv mais je n’arrive pas à filtrer pour les envoyer à des OU spécifiques du domaine AD en fonction d’une colonne du fichier csv.
    ID,Nom,Prenom,OU
    1,Samir,Follow,DI
    2,Abdoul,Kevin,VM
    3,Ali,Medah,RH
    Merci à vous

    Répondre

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Ce site utilise Akismet pour réduire les indésirables. En savoir plus sur comment les données de vos commentaires sont utilisées.