0

I have a registration form, a login form and a Main form.The program start with registration form. If i sign up the datas(name, email, password) load up to the local database. When i log in correctly show the main form. The main form has a usercontrol with a label. I would like to write a welcome text to the label with her/his name. Example: "Welcome Josh!". So I should to identify the user, so i use the textboxEmail.Text from the login form. My solution is not working. There is my code:

namespace personalFinance
{
   public partial class Login : Form
      {
        public Login()
         {

            InitializeComponent();
            var MainForm = new MainForm();
            MainForm.Show();
            HomepageUC hp = new HomepageUC(textboxEmail.Text);
            hp.Show();
         } 
      }

}
namespace personalFinance
{
    public partial class HomepageUC : UserControl
    {
       string login = "";
       public HomepageUC(string email)
          {

            InitializeComponent();
            login = email;
            var conn = new SqlConnection(@"Server=(localdb)\MSSQLLocalDB; 
            AttachDbFileName=|DataDirectory|database.mdf;");
            conn.Open();
            var cmd = new SqlCommand($"SELECT email FROM registration_data 
            WHERE email = '{login}'", conn);
            var reader = cmd.ExecuteReader();
            while (reader.Read()) labelWelcome.Text = reader[0].ToString();
          }
     }

 }

I got that error: There is no argument given that corresponds to the required formal parameter 'email' of 'HomepageUC.HomepageUC(string)' personalFinance C:\Users\nickname18\source\repos\personalFinance\personalFinance\MainForm.Designer.cs

when i click this error retrieve to MainForm.Designer.cs this.HompageUC1 = new personalFinance.Homepage1(); it is underline with red.

  • 1
    You have a SQL injection vulnerability. – SLaks Mar 26 '19 at 14:06
  • 2
    Before you write another line of code you need to read about sql injection. Your code is wide open. My friend [Bobbly Tables](http://bobby-tables.com/) loves this kind of thing. You also need to wrap your command and connection objects (and any other objects implementing IDisposable) in a USING statement. The code you have here will eat up your connection pool when multiple people use this application. – Sean Lange Mar 26 '19 at 14:08
  • thank you, for the help! – nickname18 Mar 26 '19 at 14:23
  • Added an answer with parameter+a better constructor+correct disposing. I would encourage reading about a) SQL Injection. b) Unmanaged resources (IDisposable) – Cleptus Mar 26 '19 at 14:26
  • You probably want to change that `SELECT email FROM ...` to `SELECT userName FROM ...` – Cleptus Mar 26 '19 at 14:31
  • @bradbury9, yes i saw that. i change it now. – nickname18 Mar 26 '19 at 15:34

3 Answers3

0

The WinForms designer creates user controls by calling their default constructor. Therefore, you can't define a custom constructor like that.

Instead, you should create a custom property.

SLaks
  • 868,454
  • 176
  • 1,908
  • 1,964
0

Is the email field unique? Did you already debug? Are occurs any error? Perhaps the query brought more than one record or no record, and perhaps the field was empty too. Try this:

namespace personalFinance
{
    public partial class HomepageUC : UserControl
    {
       string login = "";
       public HomepageUC(string email)
          {

            InitializeComponent();
            login = email;
            var conn = new SqlConnection(@"Server=(localdb)\MSSQLLocalDB; 
            AttachDbFileName=|DataDirectory|database.mdf;");
            conn.Open();
            var cmd = new SqlCommand($"SELECT email FROM registration_data 
            WHERE email = '{login}'", conn);
            var reader = cmd.ExecuteReader();

            while (reader.Read())
            {
                if(!string.IsNullOrEmpty(reader[0].ToString()))
                {
                    labelWelcome.Text = reader[0].ToString();
                    break;
                }
            }           
        }
    }
}
Alex Alves
  • 68
  • 4
0

You should use parametrized queries and do proper usage of unmanaged resources. An easy and quick trick to IDisposable is the using keyword

public partial class HomepageUC : UserControl
{
   string login = "";

   public HomepageUC() // Default constructor for the designer/properties inicialization
   {
       InitializeComponent();
   }

   public HomepageUC(string email): this() // Your business logic constructor calls the default one
      {

        login = email;
        var conn = new SqlConnection(@"Server=(localdb)\MSSQLLocalDB; 
        AttachDbFileName=|DataDirectory|database.mdf;");
        conn.Open();
        var cmd = new SqlCommand($"SELECT email FROM registration_data WHERE email = @email", conn);
        cmd.Parameters.AddWithValue("@email", email); // Use parameters to avoid SQLi 
        var reader = cmd.ExecuteReader();
        while (reader.Read()) labelWelcome.Text = reader[0].ToString();
        conn.Close(); // Added unmanaged resources liberation
        conn.Dispose();
      }
 }

}

Cleptus
  • 3,446
  • 4
  • 28
  • 34
  • thank you, the program don't get the error message now, but now in labelWelcome don't show the data. It show the base label text, not the database's data. – nickname18 Mar 26 '19 at 15:24
  • Is your code executed? Check [using a debugger](https://stackoverflow.com/questions/25385173/what-is-a-debugger-and-how-can-it-help-me-diagnose-problems) – Cleptus Mar 26 '19 at 15:37