Click here to Skip to main content
14,386,783 members
Rate this:
Please Sign up or sign in to vote.
See more:
Hello,
I am developing an application for a University, using C# and PostgreSQL(as the database).

For the moment, I work on Login Form and the next Form that should appear.
The Login Form contains Username, Password and Connect button.
The database table Users contains username, password and type.

I have two account types: teacher and student. And also two Main Forms: the Main Form1 that teachers use and the Main Form2 that students use.

When the user log in with an account that is assigned to teacher, the login form will close and the teacher form will open. And so with the student.
(account type: teacher -> Main Form1)
(account type: student -> Main Form2)

So far, the forms are done, but I am still trying to figure out how to write the code so that the database will check the account type and then open the desired form.

I am asking if anyone can please help or share an advice.

Below I posted the code for Connect button in Login form:
private void btnConnect_Click(object sender, EventArgs e)
        {
            try
            {
            string myConnection = "Server=x; Port=x; Database=x; UID=x; Pwd=x";

            NpgsqlConnection myConn = new NpgsqlConnection(myConnection);
            NpgsqlCommand myComm = new NpgsqlCommand("select * from Users where user='" + this.tb_user.Text + "' and password= '" + this.tb_pw.Text + "'; ", myConn);

            NpgsqlDataReader myReader;
                myConn.Open();
                myReader = myComm.ExecuteReader();
                int count = 0;
                while (myReader.Read())
                {
                    count = count + 1;
                }
                if (count == 1)
                {
                    MessageBox.Show("User and Password are correct...\nConnected!", "University");

                    this.Hide();
                    MainForm1 f1 = new MainForm1("Welcome, " + tb_user.Text.ToUpper());
                    f1.ShowDialog();
                }
                else
                {
                    MessageBox.Show("User and Password are incorrect!", "University");
                }

                myConn.Close();
            }
            catch (Exception msg)
            {
                MessageBox.Show(msg.Message);
                throw;
            }
        }   

Thank you in advance.
Posted
Comments
Richard Deeming 10-Sep-14 10:27am
   
Your code is susceptible to SQL Injection[^]. Use parameterized queries to protect your database.

Also, you shouldn't be storing passwords in plain text. You should be storing a salted hash of the password instead:
Salted Password Hashing - Doing it Right[^]
Richard Deeming 10-Sep-14 10:30am
   
Instructions for using parameters with NpgsqlCommand:
https://github.com/npgsql/Npgsql/wiki/User-Manual#using-parameters-in-a-query[^]
Stelig 10-Sep-14 10:59am
   
Thank you so much for answers!
Very useful solutions. And about salted hash...it is exceptional idea :)
Rate this:
Please Sign up or sign in to vote.

Solution 1

You need to develop a logic to determine what type of user has logged in, inside your Database create a new column, to save whether the user is a teacher or a student. It can be a single Bit column, with name of IsTeacher, and you can save 1 if the user is a teacher or 0 if the user is a student.

Once done query-ing and loggin the user in. You can get the details for that user ID or user name that user has.

// If the user that is logged in, is teacher
if(User.IsTeacher) {
   // create the form 1 instance, and show it
   Form1 form = new Form1();
   // otherwise, 
} else {
   // create the form 2 instance and show it
   Form2 form = new Form2();
}


..this is a basic logic that you can use. To show the form depending on the user, remember the logic is always based on a condition. Without a condition you can never create a logic. Once you've got the condition, you can develop the logic.
   
Rate this:
Please Sign up or sign in to vote.

Solution 2

myreader["type"] would contain the value return from the database for the user. Based on that type, you can put either a switch or if-else around showing the Main form, which can either be MainForm1 or MainForm2.

However, if you expect a single result, you could change:
while (myReader.Read())

into:
if (myReader.Read())

to make the code easier.
private void btnConnect_Click(object sender, EventArgs e)
{
    try
    {
    string myConnection = "Server=x; Port=x; Database=x; UID=x; Pwd=x";

    NpgsqlConnection myConn = new NpgsqlConnection(myConnection);
    NpgsqlCommand myComm = new NpgsqlCommand("select * from Users where user='" + this.tb_user.Text + "' and password= '" + this.tb_pw.Text + "'; ", myConn);

    NpgsqlDataReader myReader;
        myConn.Open();
        myReader = myComm.ExecuteReader();

        if (myReader.Read())
        {
            MessageBox.Show("User and Password are correct...\nConnected!", "University");

            this.Hide();

            switch (myReader["type"].ToString())
            {
                case "teacher":
                    MainForm1 f1 = new MainForm1("Welcome, " + tb_user.Text.ToUpper());
                    f1.ShowDialog();
                    break;
                case "student":
                    MainForm2 f2 = new MainForm2("Welcome, " + tb_user.Text.ToUpper());
                    f2.ShowDialog();
                    break;
                default:
                    MessageBox.Show("Error...");
                    break;
            }
        }
        else
        {
            MessageBox.Show("User and Password are incorrect!", "University");
        }

        myConn.Close();
    }
    catch (Exception msg)
    {
        MessageBox.Show(msg.Message);
        throw;
    }
}   

Pay attention to how and when you dispose of objects like the reader and the connection.
   
Rate this:
Please Sign up or sign in to vote.

Solution 3

As mentioned above, if statement works well if the roles won't change. Sometimes I like to use a dictionary as a 'switch' statement. Something like:


var lut = new Dictionary<string,>>(StringComparer.InvariantCultureIgnoreCase);

lut.Add("teacher", str => new MainForm1("Welcome, "+str));
lut.Add("student", str => new MainForm2("Welcome, "+str));
// can add more forms here for other roles, too
lut.Add("superadmin", str=> new SuperForm(str));
lut.Add("techguy", str => new TechForm(str));


//... skipping some lines
if (myReader.Read()){
    string type = myReader["type"].ToString();
    if(lut.ContainsKey(type)){
        lut[type](tb_user.Text.ToUpper()).ShowDialog();
    }
}

#IF DEBUG
    foreach(var kp in lut){
        kp.Value("DEBUG").Show(); // show all for no reason
    }
#ENDIF
   
Comments
kbrandwijk 10-Sep-14 16:05pm
   
I like this approach, because it split the logic that defines the actions from the logic to apply one. The Dictionary schould be of type Dictionary<string,func<string,form>> however. And for this specific case, it seems to violate the KISS principle.

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)




CodeProject, 503-250 Ferrand Drive Toronto Ontario, M3C 3G8 Canada +1 416-849-8900 x 100