How do I read a user attribute?

Posted on 2002-06-23
Last Modified: 2010-05-02
How do I read a user attribute (such as the "displayName" attribute) for the currently logged on user in Win2K?


Question by:jamiemoh
  • 4
  • 2

Expert Comment

ID: 7102498
Here is an API example from  Q_20175369

Private Type USER_INFO_2
   usri2_name As Long
   usri2_password  As Long  ' Null, only settable
   usri2_password_age  As Long
   usri2_priv  As Long
   usri2_home_dir  As Long
   usri2_comment  As Long
   usri2_flags  As Long
   usri2_script_path  As Long
   usri2_auth_flags  As Long
   usri2_full_name As Long
   usri2_usr_comment  As Long
   usri2_parms  As Long
   usri2_workstations  As Long
   usri2_last_logon  As Long
   usri2_last_logoff  As Long
   usri2_acct_expires  As Long
   usri2_max_storage  As Long
   usri2_units_per_week  As Long
   usri2_logon_hours  As Long
   usri2_bad_pw_count  As Long
   usri2_num_logons  As Long
   usri2_logon_server  As Long
   usri2_country_code  As Long
   usri2_code_page  As Long
End Type

Private Declare Function apiNetGetDCName _
   Lib "netapi32.dll" Alias "NetGetDCName" _
   (ByVal servername As Long, _
   ByVal DomainName As Long, _
   bufptr As Long) As Long

' function frees the memory that the NetApiBufferAllocate
' function allocates.
Private Declare Function apiNetAPIBufferFree _
   Lib "netapi32.dll" Alias "NetApiBufferFree" _
   (ByVal buffer As Long) _
   As Long

' Retrieves the length of the specified wide string.
Private Declare Function apilstrlenW _
   Lib "kernel32" Alias "lstrlenW" _
   (ByVal lpString As Long) _
   As Long

Private Declare Function apiNetUserGetInfo _
   Lib "netapi32.dll" Alias "NetUserGetInfo" _
   (servername As Any, _
   username As Any, _
   ByVal level As Long, _
   bufptr As Long) As Long

' moves memory either forward or backward, aligned or unaligned,
' in 4-byte blocks, followed by any remaining bytes
Private Declare Sub sapiCopyMem _
   Lib "kernel32" Alias "RtlMoveMemory" _
   (Destination As Any, _
   Source As Any, _
   ByVal Length As Long)

Private Declare Function apiGetUserName Lib _
   "advapi32.dll" Alias "GetUserNameA" _
   (ByVal lpBuffer As String, _
   nSize As Long) _
   As Long

Private Const MAXCOMMENTSZ = 256
Private Const NERR_SUCCESS = 0
Private Const ERROR_MORE_DATA = 234&
Private Const MAX_CHUNK = 25
Private Const ERROR_SUCCESS = 0&

Function fGetFullNameOfLoggedUser(Optional strUserName As String) As String
' Returns the full name for a given UserID
'   NT/2000 only
' Omitting the strUserName argument will try and
' retrieve the full name for the currently logged on user
On Error GoTo ErrHandler
Dim pBuf As Long
Dim dwRec As Long
Dim pTmp As USER_INFO_2
Dim abytPDCName() As Byte
Dim abytUserName() As Byte
Dim lngRet As Long
Dim i As Long

   ' Unicode
   abytPDCName = fGetDCName() & vbNullChar
   If (Len(strUserName) = 0) Then strUserName = fGetUserName()
   abytUserName = strUserName & vbNullChar

   ' Level 2
   lngRet = apiNetUserGetInfo( _
                           abytPDCName(0), _
                           abytUserName(0), _
                           2, _
   If (lngRet = ERROR_SUCCESS) Then
       Call sapiCopyMem(pTmp, ByVal pBuf, Len(pTmp))
       fGetFullNameOfLoggedUser = fStrFromPtrW(pTmp.usri2_full_name)
   End If

   Call apiNetAPIBufferFree(pBuf)
   Exit Function
   fGetFullNameOfLoggedUser = vbNullString
   Resume ExitHere
End Function

Private Function fGetUserName() As String
' Returns the network login name
Dim lngLen As Long, lngRet As Long
Dim strUserName As String
   strUserName = String$(254, 0)
   lngLen = 255
   lngRet = apiGetUserName(strUserName, lngLen)
   If lngRet Then
       fGetUserName = Left$(strUserName, lngLen - 1)
   End If
End Function

Function fGetDCName() As String
Dim pTmp As Long
Dim lngRet As Long
Dim abytBuf() As Byte

   lngRet = apiNetGetDCName(0, 0, pTmp)
   If lngRet = NERR_SUCCESS Then
       fGetDCName = fStrFromPtrW(pTmp)
   End If
   Call apiNetAPIBufferFree(pTmp)
End Function

Private Function fStrFromPtrW(pBuf As Long) As String
Dim lngLen As Long
Dim abytBuf() As Byte

   ' Get the length of the string at the memory location
   lngLen = apilstrlenW(pBuf) * 2
   ' if it's not a ZLS
   If lngLen Then
       ReDim abytBuf(lngLen)
       ' then copy the memory contents
       ' into a temp buffer
       Call sapiCopyMem( _
               abytBuf(0), _
               ByVal pBuf, _
       ' return the buffer
       fStrFromPtrW = abytBuf
   End If
End Function

Private Sub Command1_Click()
MsgBox fGetFullNameOfLoggedUser(Text1.Text)
End Sub


Expert Comment

ID: 7102499
Or the Eviron method like this;

MsgBox Environ("UserName")


The WSH method (from wsh2 Q_20175369);

  Dim wshNetwork As Object
  Set wshNetwork = CreateObject("Wscript.Network")
  With wshNetwork
     MsgBox "Computer Name: " & .ComputerName & vbCrLf _
        & "User Name: " & .UserName
  End With

Author Comment

ID: 7102506
Sorry I should have been more specific. I want to do this in VBScript as part of a logon script.

Also I want to be able to read an attribute or the currently logged on user.

The following code reads the displayName attribute:

Set objUser = GetObject ("LDAP://CN=jbloggs,CN=Users,DC=mycompany,DC=com")

strdisplayName = objUser.Get("displayName")
WScript.echo "displayName = " & strdisplayName

HOWEVER I have to manually enter the ("LDAP://CN=jbloggs...") part. I need to do this for the currently logged on user.

Free Trending Threat Insights Every Day

Enhance your security with threat intelligence from the web. Get trending threat insights on hackers, exploits, and suspicious IP addresses delivered to your inbox with our free Cyber Daily.


Accepted Solution

xSinbad earned 75 total points
ID: 7102693
Oh I am not a great exponent of VBScript but if you look at the example above your last comment, it uses the Windows Scripting Host which esentially is VBScript and shuold therefore will a little modification work for you.

Something like;

Dim wshNetwork
 Set wshNetwork = CreateObject("Wscript.Network")
 With wshNetwork
    MsgBox "Computer Name: " & .ComputerName & vbCrLf _
       & "User Name: " & .UserName
 End With


Author Comment

ID: 7102805
Thats gives me the currently logged on users name but i want to be able to use this to read an attribute of this user..i.e. the distinuished name value

Expert Comment

ID: 7106275
Is this on a Novel network ("CN")?

Below is a sample from what you have that will use my code to get the username to place in the string strGet thus hopefully doing what you ask.

Function userN()
Dim wshNetwork
 Set wshNetwork = CreateObject("Wscript.Network")
 With wshNetwork
   testit = .UserName
 End With
end function

function getname()
dim objUser
dim strdisplayName
dim strGet
strGet = "LDAP://CN=" & userN & ",CN=Users,DC=mycompany,DC=com"
msgbox strget
Set objUser = GetObject strGet)
strdisplayName = objUser.Get("displayName")
WScript.echo "displayName = " & strdisplayName
end function
LVL 49

Expert Comment

ID: 9664196
Hi jamiemoh,
It appears that you have forgotten to close this question. I will ask Community Support to close it unless you finalize it within 7 days. I will ask a Community Support Moderator to:

    Split points between: xSinbad

jamiemoh, if you think your question was not answered at all or if you need help, just post a new comment here; Community Support will help you.  DO NOT accept THIS comment as an answer.

EXPERTS: If you disagree with that recommendation, please post an explanatory comment.
DanRollins -- EE database cleanup volunteer

Featured Post

How to improve team productivity

Quip adds documents, spreadsheets, and tasklists to your Slack experience
- Elevate ideas to Quip docs
- Share Quip docs in Slack
- Get notified of changes to your docs
- Available on iOS/Android/Desktop/Web
- Online/Offline

Join & Write a Comment

Suggested Solutions

Background What I'm presenting in this article is the result of 2 conditions in my work area: We have a SQL Server production environment but no development or test environment; andWe have an MS Access front end using tables in SQL Server but we a…
I was working on a PowerPoint add-in the other day and a client asked me "can you implement a feature which processes a chart when it's pasted into a slide from another deck?". It got me wondering how to hook into built-in ribbon events in Office.
As developers, we are not limited to the functions provided by the VBA language. In addition, we can call the functions that are part of the Windows operating system. These functions are part of the Windows API (Application Programming Interface). U…
Show developers how to use a criteria form to limit the data that appears on an Access report. It is a common requirement that users can specify the criteria for a report at runtime. The easiest way to accomplish this is using a criteria form that a…

758 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

21 Experts available now in Live!

Get 1:1 Help Now