2008-12-21 5 views
19

Comment créer un compte d'utilisateur local à l'aide de .NET 2.0 et C# et pouvoir également définir le "Mot de passe n'expire jamais" pour jamais.Création d'un compte d'utilisateur local C# et .NET 2.0

J'ai essayé d'utiliser "Net.exe" en utilisant Process.Start et en transmettant ses paramètres, mais il semble que "net user" ne puisse pas définir le "Mot de passe n'expire jamais" jamais.

Répondre

21

Lire cet excellent article CodeProject

Howto: (Almost) Everything In Active Directory via C#

Il y a une section "Créer un compte utilisateur" et "Faire face à l'utilisateur des mots de passe".

MISE À JOUR:

Pour adapter le code pour les comptes locaux remplacent les lignes respectives avec ces:

DirectoryEntry localMachine = new DirectoryEntry("WinNT://" + 
    Environment.MachineName); 
DirectoryEntry newUser = localMachine.Children.Add("localuser", "user"); 

commence ici l'extrait de code d'origine pour les comptes de domaine:

public string CreateUserAccount(string ldapPath, string userName, 
    string userPassword) 
{ 
    string oGUID = string.Empty; 
    try 
    {   
     string connectionPrefix = "LDAP://" + ldapPath; 
     DirectoryEntry dirEntry = new DirectoryEntry(connectionPrefix); 
     DirectoryEntry newUser = dirEntry.Children.Add 
      ("CN=" + userName, "user"); 
     newUser.Properties["samAccountName"].Value = userName; 

     int val = (int)newUser.Properties["userAccountControl"].Value; 
     newUser.Properties["userAccountControl"].Value = val | 0x10000; 

     newUser.CommitChanges(); 
     oGUID = newUser.Guid.ToString(); 

     newUser.Invoke("SetPassword", new object[] { userPassword }); 
     newUser.CommitChanges(); 

     dirEntry.Close(); 
     newUser.Close(); 
    } 
    catch (System.DirectoryServices.DirectoryServicesCOMException E) 
    { 
     //DoSomethingwith --> E.Message.ToString();  
    } 
    return oGUID; 
} 

Il y a quelques détails pour comprendre lorsqu'ils traitent avec des mots de passe de l'utilisateur et limites autour des mots de passe tels que forcer un utilisateur à changer leur mot de passe sur la prochaine ouverture de session, déniant l'utilisateur le droit de modifier leurs propres mots de passe, des mots de passe pour ne jamais expirer, à expirer, et ces tâches peuvent être accomplies en utilisant les indicateurs UserAccountControl qui sont démontrés dans les sections .

S'il vous plaît se référer à ce grand MSDN article: Managing User Passwords des exemples et la documentation concernant ces caractéristiques.

CONST       HEX 
------------------------------------------ 
SCRIPT       0x0001 
ACCOUNTDISABLE     0x0002 
HOMEDIR_REQUIRED    0x0008 
LOCKOUT      0x0010 
PASSWD_NOTREQD     0x0020 
PASSWD_CANT_CHANGE    0x0040 
ENCRYPTED_TEXT_PWD_ALLOWED  0x0080 
TEMP_DUPLICATE_ACCOUNT   0x0100 
NORMAL_ACCOUNT     0x0200 
INTERDOMAIN_TRUST_ACCOUNT  0x0800 
WORKSTATION_TRUST_ACCOUNT  0x1000 
SERVER_TRUST_ACCOUNT   0x2000 
DONT_EXPIRE_PASSWORD   0x10000 
MNS_LOGON_ACCOUNT    0x20000 
SMARTCARD_REQUIRED    0x40000 
TRUSTED_FOR_DELEGATION   0x80000 
NOT_DELEGATED     0x100000 
USE_DES_KEY_ONLY    0x200000 
DONT_REQ_PREAUTH    0x400000 
PASSWORD_EXPIRED    0x800000 
TRUSTED_TO_AUTH_FOR_DELEGATION 0x1000000 
+0

Les liens que vous avez spécifiés sont pour le répertoire actif. Peut-être que je n'étais pas clair. Je veux changer de compte d'utilisateur local (L'ordinateur ne fait pas partie d'un répertoire actif). – mrtaikandi

+0

Autant que je m'en souvienne, cela devrait s'appliquer aussi aux comptes locaux. – splattne

+0

@ Mohammadreza: J'ai mis à jour ma réponse. Maintenant, il y a du code qui gère les comptes locaux – splattne

21

Ce code va créer un compte local avec le mot de passe n'expire jamais ensemble:

 using System.DirectoryServices; 

     DirectoryEntry hostMachineDirectory = new DirectoryEntry("WinNT://localhost"); 
     DirectoryEntries entries = hostMachineDirectory.Children; 
     bool userExists = false; 
     foreach (DirectoryEntry each in entries) 
     { 
      userExists = each.Name.Equals("NewUser", 
      StringComparison.CurrentCultureIgnoreCase); 
      if (systemtestUserExists) 
       break; 
     } 

     if (false == userExists) 
     { 
      DirectoryEntry obUser = entries.Add("NewUser", "User"); 
      obUser.Properties["FullName"].Add("Local user"); 
      obUser.Invoke("SetPassword", "[email protected]"); 
      obUser.Invoke("Put", new object[] {"UserFlags", 0x10000}); 
      obUser.CommitChanges(); 
     } 

Le drapeau 0x10000 signifie PasswordNeverExpires.

J'ai passé beaucoup de temps à déterminer comment créer un compte utilisateur local avec le mot de passe défini pour ne pas expirer. Il semble que lorsque vous essayez d'utiliser:

int val = (int)newUser.Properties["userAccountControl"].Value; 
newUser.Properties["userAccountControl"].Value = val | 0x10000 

les autorisations du répertoire actif entrent en jeu. Si vous disposez d'autorisations de répertoire actives, tout fonctionne correctement. Si vous n'obtenez pas la propriété userAccountControl, la valeur null sera toujours définie. Essayer de définir userAccountControl entraînera une exception "La propriété de répertoire ne peut pas être trouvée dans le cache".

Cependant, après beaucoup de chasse, j'ai trouvé une autre propriété "UserFlags" qui doit être définie en utilisant Invoke. Vous pouvez l'utiliser pour définir l'indicateur sur un compte local. J'ai essayé ce code et cela a fonctionné sur Windows Server 2008.

Espérons que cela aide

+0

Nice one, +1. Quelques notes: d'abord, DirectoryEntry est jetable, donc mieux vaut l'utiliser avec {}; en second lieu, le constructeur DirectoryEntry peut prendre un nom d'ordinateur distant si vous devez créer un utilisateur local sur une boîte distante. –

0

en utilisant System.DirectoryServices;

DirectoryEntry hostMachineDirectory = new DirectoryEntry("WinNT://localhost"); 
    DirectoryEntries entries = hostMachineDirectory.Children; 
    bool userExists = false; 
    foreach (DirectoryEntry each in entries) 
    { 
     userExists = each.Name.Equals("NewUser", 
     StringComparison.CurrentCultureIgnoreCase); 
     if (systemtestUserExists) 
      break; 
    } 

    if (false == userExists) 
    { 
     DirectoryEntry obUser = entries.Add("NewUser", "User"); 
     obUser.Properties["FullName"].Add("Local user"); 
     obUser.Invoke("SetPassword", "[email protected]"); 
     obUser.Invoke("Put", new object[] {"UserFlags", 0x10000}); 
     obUser.CommitChanges(); 
Questions connexes