Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations strongm on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Create a logon form 2

Status
Not open for further replies.

MichelleButler

IS-IT--Management
Apr 5, 2002
73
GB
How do I get users to logon onto the database through a form and be able to track how many users log on to the database. The password would be stored into a table, and hopefully I would like to be able to get a date time of everybody who logs in. Your help would be much appreciated.

Michelle
 
Hi, does it need to be password protected or are you doing this to log the user name?
 
Hi

You could implement Access Security, this would force a log in and ensure users have a password.

Alternatively you can create a simple form with two text boxes UsersId, password

Things you might need to know to achieve this are:

there is a setting in the format of a text box control for passwords, this will hide the data typed by displaying *'s

Application.quit will exit the app if the password check fails

Anything else you need?



Regards

Ken Reay
Freelance Solutions Developer
Boldon Information Systems Ltd
Website needs upgrading, but for now - UK
 
This is a long answer for such a short question but it's cool if your not bothered about password protecting and it can be used for loads of other stuff...

First, build a log table, call it "sysLog" and include 5 fields (names aren't important but order is).
TIME, format = date/time
COMPUTER_NAME, format = text
USER_NAME, format = text
LOG_TYPE, format = text

Then build a form to use as a splash screen, on the on timer event change add code similar to below to the form on timer event, add some welcoming text and increase the timer interval to 500 or something:
Code:
Private Sub Form_Timer()
AddToLog "LOGGED_ON"       ' add event to log

DoCmd.OpenForm "Next_Form_Name"     ' open next form
DoCmd.Close acForm, Me.Name
End Sub

then create a module to hold some code that will write to the log, code will look like this
Code:
Public Sub AddToLog(ByRef logType As String)
Dim cnn As ADODB.Connection
Dim sysLog As ADODB.Recordset
Dim c As New cComputer

On Error Resume Next

Set cnn = CurrentProject.Connection     ' set up database connection
Set sysLog = New ADODB.Recordset        ' open the recordset
sysLog.Open "sysLog", cnn, adOpenForwardOnly, adLockOptimistic, adCmdTable
With sysLog
    ' add new record and values
    .AddNew
    .Fields(0) = Now()
    .Fields(1) = c.Name     ' computer name
    .Fields(2) = c.UserName     ' NT user named
    .Fields(3) = logType        ' as passed, string field
    .Update         ' update the record and close
    .Close
End With

End Sub
code wont compile yet as there's a user defined type we've not defined yet!

create a class module called cComputer and add the following code to it
Code:
Option Compare Database
Option Explicit

Private Declare Function WNetGetUser _
    Lib "mpr.dll" Alias "WNetGetUserA" _
    (ByVal lpName As String, ByVal lpUserName As String, lpnLength As Long) As Long

Private Declare Function GetComputerName _
    Lib "kernel32" Alias "GetComputerNameA" _
    (ByVal lpBuffer As String, nSize As Long) As Long

Property Get Name() As String
Name = GetName
End Property

Property Get UserName() As String
UserName = GetUserName
End Property

Private Function GetName() As String
' Function to return computer name
Dim returnValue As Long
Dim bufferSize As Long
Dim buffer As String

' Make the buffer big enough for the name plus a vbNullChar
bufferSize = 16
buffer = String$(bufferSize, vbNullChar)
returnValue = GetComputerName(buffer, bufferSize)       ' call API

' if we've got the name then return as string
If CBool(returnValue) Then
    GetName = Left(buffer, bufferSize)
End If
    
End Function

Private Function GetUserName() As String
' function to return user name
Dim nameLength As Long
Dim UserName As String
Dim returnValue As Long

Do      ' no more data
    UserName = String$(nameLength, vbNullChar)
    returnValue = WNetGetUser(vbNullString, UserName, nameLength)       ' call API
Loop Until returnValue <> 234

If returnValue = 0 Then
    GetUserName = TrimNull(UserName)
End If
    
End Function


Private Function TrimNull(ByVal dodgyString As String) As String
Dim pos As Integer

pos = InStr(dodgyString, vbNullChar)
If pos > 1 Then
    TrimNull = Left$(dodgyString, pos - 1)
        Else
        TrimNull = dodgyString
End If

End Function

finally set the splash form as your startup form in startup options and it should log the time, computer name, user name, a log type of LOG_ON and you can use the log to add other comments like errors (by adding a memo field, which I took off to keep things shorter).

Hope this helps, Jamie

P.S. apologies again for the long answer - if there's a way to add an attachment let me know and I'll use that in future
 
Thank you very much for your quick replies, what Ideally I would like is to create a log on form, that allows users to log on, using a username and password, when they log on the this updates a table and insert a date stamp onto the table.

I hope this makes sense.

Michelle
 
Hi, whether you use built-in Access security features depends on how secure you want the database and how much coding your prepared to do.

If your not too worried, but just dont want casual users opening it then, as Ken says, a simple form with a couple of text boxes will put off most snoopers. To log the opening of the database adapt the 'AddToLog' function above but loose the cComputer class and pass it the logon name instead once the password has been accepted as correct. Unfortunately holding shift whilst opening the database would bypass this anyway!

If you want a really secure database then you will have to use Access built-in security. Again you can adapt the addtolog code so that it captures the user name (application.currentuser, I think) just add it to a splash screen, as before, but loose the cComputer class.

If your not that fussed about security but want to know who logged on when then try the code above...

Hope this helps, Jamie
 
Hi, To anyone that might read this read - I thought I should mention that the code for the above cComputer class is adapted from code in the Access 97 Developers Handbook by Sybex - I'm not sure if its copyrighted or anything but I dont wont to get in trouble for sharing it without stating it as the original source!
 
jksmi,

The code above for getting the computer name.. could you not just use Environ("ComputerName") ... This would give the same result, but a lot less coding. Also use Environ("UserName") for the NT username.
 
Hi, yes - I didn't know that. This is just something I picked up when I was using Access 97.

Where did you get the listing of expressions from? I've been looking through MSDN but cant find them...

Thanks, Jamie
 
Hi, answered my own question - but looks like I can update quite a few of my API calls to environ so very helpful, Thanks!

Code:
Sub testEnviron()
Dim i As Integer
on error resume next    ' cheat
For i = 1 To 100
    If Len(Environ$(i)) > 0 Then Debug.Print i & " : " &Environ$(i)
Next i
End Sub
 
Thanks for the star, glad you solved the Environ list question :D

Michelle,

If you are creating a small application that is going to be used by only a few people, then a bespoke 'login' form solution would be ideal - as suggested above, the security of this method is not particularly good, but it serves the purpose of logging user details.

To 'stamp' each field, when it is altered would require a little more coding on each form... as well as a change to your tables..

e.g. create two further fields on each table .. one called "aUserName" and a scond "aTimestamp" (the 'a' indicates that it is an audit field to me; just something I've always programmed with).

Assuming your user has logged into the database, you could hold their username in a global variable .. e.g. open a new module and stick in a Public variable gstrUserName for example.

Finally, I generally update records through recordsets - just need to add a couple of extra lines to the code when updating the recordset.. e.g.

With rs
.AddNew
rs!SomeField = txtMyField
rs!aTimeStamp = Now
rs!aUserName = gstrUserName
.Update
End With

Seriously consider how big this project is going to be - if it is going to be used by 50+ users on a daily basis, I'd upsize to SQL anyway .. the full benefits of SQL are beyond this question, but it does allow you to create things such as triggers.. so when data is altered, even directly in a table, you can track the user who made that alteration..

I'm in a waffling mood, so let me know if you need more info on either solution above :D

 
Hi SiJP,

Thanks for the information, I have upsized it to SQL, unfortunately the company I work for (MOD), is way behind times and it is very hard to get software to work correctly until they ungrade all the workstations to windows 2000/office 2000. Everybody is on Office 97/windows NT. I have upgraded the database successfully in windows XP working ideally with SQL 2000 but I can not get the same results on windows NT/Office 97 to SQL 7. I am very concerned at the rate the database is growing. The advice you give me sound really good, I would need to look into this one. I have the logon working, and accessing the create forms in the table.

Many thanks

Michelle
 
No problem, glad to help.

If your backend tables are SQL then it makes your life as an admin simpler, and this opens the door to locking down pretty much anything that threatens to move (or on the flip side allows as much freedom as you care to generously give).

If you'd like any suggestions on this matter, or indeed help in other areas, please feel free to post away :D

Si

------------------------
Hit any User to continue
 
Hi
Interesting topic

Is there a way to log when a user closes access
so thet the time a user logged on is recorded
and the time they quit (other than relying on the user to actually logg out)
By doing so a query could be run against the tabel which would show only users currently logged on?

Thanks
 
Well, one method of doing this would be to create a form that is hidden at startup.

In this forms Unload event put your loggin code (e.g. capture the login details, time). when the DB is closed, this form will be closed as well.. and should log the details.

But before going off to design that.. are you using access security with an MDW? If so, you can use the jet roster to see who is logged in at any one time anyway.. Heres a link to it:
Hope these help.

------------------------
Hit any User to continue
 
I don't think there is a specific article for it, however, I just testing the code in access 97 without error...

Try this..

1) Put the following code into a new module and save as Module1 or whatever.

Code:
Public Sub Whois()
    Dim cn As New ADODB.Connection
    Dim cn2 As New ADODB.Connection
    Dim rs As New ADODB.Recordset
    Dim i, j As Long
    Dim myDB As String

    myDB = InputBox("Please enter the full path of a database", "Select Database")

    cn.Provider = "Microsoft.Jet.OLEDB.4.0"
    cn.Open "Data Source=" & myDB
    cn2.Open "Provider=Microsoft.Jet.OLEDB.4.0;" & "Data Source=" & myDB

    Set rs = cn.OpenSchema(adSchemaProviderSpecific, , "{947bb102-5d43-11d1-bdbf-00c04fb92675}")

    'Output the list of all users in the current database.

    Debug.Print rs.Fields(0).Name, "", rs.Fields(1).Name, "", rs.Fields(2).Name, rs.Fields(3).Name

    While Not rs.EOF
        Debug.Print rs.Fields(0), rs.Fields(1), rs.Fields(2), rs.Fields(3)
        rs.MoveNext
    Wend

End Sub

2) Select the first line of the function and press F8 to step into the code.. F5 to run from there.. you'll be prompted for your db location by an input box..

once the code has run, pressg ctrl+g to bring up the debug window.. if you get a list of your users, then it has worked.

------------------------
Hit any User to continue
 
Thanks for your help - Much apreciated!

Is there something I need to register
as I gat errors

Dim cn As New ADODB.Connection
Dim cn2 As New ADODB.Connection
Dim rs As New ADODB.Recordset

User defined type not defined
 
Hi

You need a reference to ado library

are you by chance using Access97?, in which case DAO is default I/O library, after that default is ADO

Regards

Ken Reay
Freelance Solutions Developer
Boldon Information Systems Ltd
Website needs upgrading, but for now - UK
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top