Checking Password Field - Invalid procedure call or argument

Local time
Today, 12:44
Joined
Sep 14, 2020
Messages
43
Good morning,
I am looking too hard and suspect I can't see the obvious error in my ways - noting I an new to this.
If I enter a correct Username and leave the Password field blank my code seems crash - see "CRASH" below as comment
Any guidance will be most welcome

Thanking you
Peter

Code:
'======================================================================
'   NAME:       frmLogin
'   PURPOSE:    Login form restricting access to application
'   AUTHOR:     Peter Peterson
'   DATE:       July 2021
'======================================================================
Option Compare Database
Option Explicit

'-----------------------------------------------------------------------
'   Name:       btnExit_Click
'   Purpose:    Close the Login form
'-----------------------------------------------------------------------
Private Sub btnExit_Click()

On Error GoTo Err_btnExit_Click           ' Initialise error handling

        DoCmd.Close                         ' Close the Login form

Exit_btnExit_Click:
    Exit Sub

Err_btnExit_Click:
    MsgBox Err.Description
    Resume Exit_btnExit_Click
    
End Sub

'---------------------------------------------------------------------------
'   Name:       btnLogin
'   Purpose:    The check the credentials of the user and determine
'               whether they can gain access to the application.
'----------------------------------------------------------------------------
Private Sub btnLogin_Click()

    Dim rs As Recordset
    Dim myUsername As String
    Dim myPassword As String
    
On Error GoTo Err_btnLogin_Click

    Set rs = CurrentDb.OpenRecordset("tblUsers", dbOpenSnapshot, dbReadOnly)
    
    ' Check if Username field is empty - if so, reset username and password fields
    If IsNull(Me.txtUserName) Or Me.txtUserName = "" Then
        MsgBox "Username is empty.  You must enter a valid Username.", vbOKOnly, "LOGIN Error"
        Me.txtPassword.SetFocus
        Me.txtPassword.Text = ""
        Me.txtUserName.SetFocus
        Me.txtUserName.Text = ""
        Exit Sub
    Else
        ' Check if Username is correct
        Me.txtUserName.SetFocus
        myUsername = Me.txtUserName.Text
        If rs!UserName <> Me.txtUserName Then
            ' If Username incorrect - reset Password and Username fields
            MsgBox "Incorrect Username entered.", vbOKOnly, "LOGIN Error"
            Me.txtPassword.SetFocus
            Me.txtPassword.Text = ""
            Me.txtUserName.SetFocus
            Me.txtUserName.Text = ""
            Exit Sub
        Else
            MsgBox "CORRECT USERNAME", vbOKOnly, "LOGON Progressing"
        End If
    End If
    
    ' Check if Password field is empty
    MsgBox "checking password is not empty"
    If IsNull(Me.txtPassword) Or Me.txtPassword = "" Then ' Seems to CRASH here???
        MsgBox "Password is empty.  You must enter a Password.", vbOKOnly, vbInformation, "LOGIN Error"
        Me.txtPassword.SetFocus
        Me.txtPassword.Text = ""
        Exit Sub
    Else
        ' Check if Password is correct
        Me.txtPassword.SetFocus
        myPassword = Me.txtPassword.Text
        If rs!UserPassword <> Me.txtPassword Then
            MsgBox "Incorrect Password entered.", vbOKOnly, "LOGIN Error"
            Me.txtPassword.SetFocus
            Me.txtPassword.Text = ""
            Exit Sub
        Else
            MsgBox "Password Correct", vbOKOnly, "LOGIN Successful"
            DoCmd.Close acForm, "frmLogin"
            DoCmd.OpenForm "frmMain"
        End If
    End If

Exit_btnLogin_Click:

    DoCmd.Close
    Exit Sub
    
Err_btnLogin_Click:
    MsgBox Err.Description
    Resume Exit_btnLogin_Click
    
End Sub
 
I wouldn't use the the property "Text"as shown here:- Me.txtPassword.Text = "" I would do it like this:- Me.txtPassword = ""
 
I don't think you need to set the focus like you do here, unless there's something I'm missing:-
Me.txtUserName.SetFocus
myUsername = Me.txtUserName.Text

Just do this:-
myUsername = Me.txtUserName
 
I don't think you need to do this:-

Me.txtPassword.SetFocus


This line should work ok:-
If rs!UserPassword <> Me.txtPassword Then

But seeing as you have set the variable "myPassword" to the textbox "Me.txtPassword" then it should read

If rs!UserPassword <> myPassword Then

You could use either, but if you use the first option then setting the variable "myPassword" is superfluous and that line could be deleted.
 
It's usually best to dim the Recordset as a DAO Recordset or an ADO Recordset, although by default, these days, it's DAO
 
I'm not sure these are in the right order. I reckon you're closing the login form before you open the main form. I reckon they should be round the other way, but I can't check it out in an MS Access DB the moment!

DoCmd.Close acForm, "frmLogin"
DoCmd.OpenForm "frmMain"

I reckon this would be better:-

DoCmd.OpenForm "frmMain"
DoCmd.Close acForm, "frmLogin"
 
Thank you @Uncle Gizmo for your numerous comments.
I am taking all them into consideration and will try and see if they make a difference.
I'll come back with a comment later today.
Cheers Peter
 
I don't see where you navigate in that recordset to match or not match the data the user entered. I see where you open the recordset.
What you need to do at some point is look into the table, and see if the data the user entered is in there. Consider something like...
Code:
Private Sub btnLogin_Click()
    Const SQL As String = _
        "SELECT Count(*) As CredentialsOK " & _
        "FROM tblUser " & _
        "WHERE User = p0 " & _
            "AND Pass = p1"
    
    With CurrentDb.CreateQueryDef("", SQL)
        .Parameters(0) = Me.txtUsername
        .Parameters(1) = Me.txtPassword
        If .OpenRecordset.Fields("CredentialsOK") Then
            DoCmd.Close acForm, Me.Name
            DoCmd.OpenForm "fMain"
        Else
            MsgBox "Epic Fail!", vbCritical
            Me.txtUsername = Null
            Me.txtPassword = Null
        End If
        .Close
    End With
End Sub
What that query does is counts the rows that match txtUsername and txtPassword. If there is more than zero of them, then the user is in. Maybe this can give some ideas.
Mark
 
You can also use DCount()?
Code:
'---------------------------------------------------------------------------
'   Name:       btnLogin
'   Purpose:    The check the credentials of the user and determine
'               whether they can gain access to the application.
'----------------------------------------------------------------------------
Private Sub btnLogin_Click()

    Dim myUsername As String
    Dim myPassword As String
    
On Error GoTo Err_btnLogin_Click

    ' Check if Username field is empty - if so, reset username and password fields
    If Len(Me.txtUserName & "") < 1 Then
        MsgBox "Username is empty.  You must enter a valid Username.", vbOKOnly, "LOGIN Error"
        Me.txtUserName.SetFocus
        Exit Sub
    End If
    If Len(Me.txtPassword & "") < 1 Then
        MsgBox "Passwrd is empty.  You must enter a valid Password.", vbOKOnly, "LOGIN Error"
        Me.txtPassword.SetFocus
        Exit Sub
    End If
    If DCount("1", "tblUsers", "UserName = '" & Me.txtUserName & "' And Password = '" & Me.txtPassword & "'") Then
        MsgBox "CORRECT USERNAME and PASSWORD", vbOKOnly, "LOGON Progressing"
    Else
        MsgBox "Invalid Username or Password", vbOKOnly, "LOGIN Error"
        Exit Sub
    End If
    
    DoCmd.OpenForm "frmMain"
    DoCmd.Close acForm, "frmLogin"

Exit_btnLogin_Click:

    DoCmd.Close
    Exit Sub
    
Err_btnLogin_Click:
    MsgBox Err.Description
    Resume Exit_btnLogin_Click
    
End Sub
 

Users who are viewing this thread

Back
Top Bottom