Programming
November 25, 2018

Приложение на C# + связка с MySQL базой данных

Привет всем кодерам! В этом мини-туториале мы с вами с нуля напишем десктопное приложение на С#, которое будет работать с базой данных. Это задание было дано учебной программой 11 класса НИШ ФМН г.Алматы.


Что мы будем для этого использовать?

  • Среда программирования: Visual Studio 2017 (версия не имеет никакого значения)
  • Языки: C# - для клиентской части приложения, MySQL - для работы с данными в базе данных нашего приложения

Что будет выполнять приложение?

Наше приложение будет добавлять, изменять, обновлять, удалять и запрашивать данные из базы данных каратистов. "А почему каратистов?" - спросите вы. Так потому что это самая родная для меня тема, вот и будем рассматривать данный пример.


Создание проекта

После того, как вы скачали Visual Studio себе на компьютер, вам следует создать проект.

Как это сделать?

Создать проект -> Visual C# -> Приложение Windows Forms -> *Выбираем название для проекта и его расположение* -> OK

Теперь у вас готов проект и можно приступать к работе!


Создание форм (Часть 1)

Теперь нам нужно создать графический интерфейс приложения через формы. Добавлять новые формы легко. Просто нажимаете правой кнопкой мыши на свой проект и выбираете "Добавить", как на скриншоте ниже:

Далее следует поработать над дизайном наших форм. Не будем сильно изощряться и сделаем максимально минималистичный дизайн:

Главное меню

Меню выбора

Меню выбора для редактирования

Форма для добавления нового пользователя

Так-с. Дальше пока что мы не пойдём, так как для начала нам нужно понять как всё будет работать. У нас есть форма для добавления каратиста, и нам еще нужны формы для создания запросов, для просмотра базы данных и для редактирования её. Но где сама база данных?

Её нет. Поэтому нам нужно немедленно её создать!


Создание базы данных

Переходим во вкладку "Средства" и выбираем "Подключиться к базе данных". Далее открывается окно "Добавить подключение", где в поле "Источник данных" мы выбираем "Файл базы данных Microsoft SQL Server (SqlClient)". Даём любое название файлу базы данных, в нашем случае - "IOGKF_members". Далее нажимаем кнопку "ОК" и в левой стороне экрана видим, как у нас добавилась новая база данных.

Раскрываем директорию с нашей базой данных и видим самую первую папку "Таблицы" - она нас и интересует. Жмём по ней правой кнопкой мыши и нажимаем "Добавить новую таблицу".

Можно создать таблицу двумя путями: 1) Конструктором 2) Через SQL код

Если вам лень делать её самим, то скопируйте следующий SQL код и вставьте его в поле с кодом у таблицы:

CREATE TABLE [dbo].[Members] (
    [member_id]  INT          NOT NULL,
    [last_name]  VARCHAR (20) NULL,
    [first_name] VARCHAR (20) NULL,
    [age]        INT          NULL,
    [rank]       VARCHAR (3)  NULL,
    [rank_value] INT          NULL,
    [sensei]     VARCHAR (20) NULL,
    [dojo]       VARCHAR (20) NULL,
    PRIMARY KEY CLUSTERED ([member_id] ASC)
);

Коротко о типах данных в SQL

  • varchar - тот же самый String, то есть строка (в скобках пишем её максимальную длину)
  • int - целые числа
  • binary - тот же самый boolean, то есть True or False, только в SQL - это 1 и 0 соответственно

И еще...

null - указываем может ли переменная быть пустой, то есть не содержать информации

primary key - первичный ключ, в данном случае это member_id. Таким образом, все значения member_id уникальны

После того как вы создали таблицу, нужно её сохранить. Нажмите ctrl + s или просто закройте файл с таблицей после чего у вас появится сообщение о сохранении таблицы.

Ок, теперь у нас есть база данных и таблица, где будет храниться информация о каратистах.


Создание форм (Часть 2) + код

Давайте напишем программный код для добавления каратистов в нашу базу данных. В моём проекте эта форма называется Form5 (у неё надпись "Add User" в предыдущих скриншотах). В классе этой формы пишем следующее:

public string conString = "Data Source=(LocalDB)\\MSSQLLocalDB;AttachDbFilename=C:\\Users\\HP\\Desktop\\IOGKF\\IOGKF\\IOGKF_members.mdf;Integrated Security=True;Connect Timeout=30";

Здесь мы создали строковую переменную conString и присвоили ей значение строки подключения базы данных. Чтобы посмотреть вашу строку подключения нажмите правой кнопкой мыши по базе данных и выберите "Свойства":

Теперь два раза нажимаем на кнопку "Add" в конструкторе нашей формы и таким образом открываем код, который будет выполняться при её нажатии. Вот код метода, который выполняется при нажатии:

private void button1_Click(object sender, EventArgs e)
        {
            SqlConnection con = new SqlConnection(conString);

            con.Open();

            if(con.State == System.Data.ConnectionState.Open)
            {
                string q = "insert into Members(member_id, last_name, first_name," +
                    " age, rank, rank_value, sensei, dojo)" +
                    " values('" + textBox1.Text.ToString() + "','" + textBox2.Text.ToString() + "','" + textBox3.Text.ToString() + "','" + textBox4.Text.ToString() + "','" + comboBox2.Text.ToString() + "','" + comboBox1.Text.ToString() + "','" + comboBox3.Text.ToString() + "','" + textBox8.Text.ToString() + "') ";
                SqlCommand cmd = new SqlCommand(q, con);
                cmd.ExecuteNonQuery();
                MessageBox.Show("Connection was successful!");
            }

            con.Close();
        }

Мы создаём объект con типа SqlConnection и если наша база данных подключена к приложению у нас будет выполняться код находящийся под блоком if. Там у нас сохранена SQL команда в строке q, которая позже передаётся в объект cmd типа SqlCommand, который позже выполняет функцию ExecuteNonQuery, которая выполняет данный SQL запрос. После при успешном выполнении в приложении выведется сообщение об успешном добавлении каратиста. Всё достаточно просто!

Кстати, как работают кнопки навигации в приложении, то есть для перехода между формами?

Вот держите пример кода, по этому шаблону они все и работают:

private void button3_Click(object sender, EventArgs e)
        {
            this.Visible = false;
            Form3 form3= new Form3();
            form3.ShowDialog();
        }

Далее давайте напишем код для формы с обычным просмотром базы данных. Допустим, что мы уже заполнили базу данных и она должна выглядить так при работе приложения:

Чтобы ��рийти к такому результату нам нужно добавить в нашу форму DataGridView, объект, который будет отображать таблицу. Сделать это очень просто, на скриншоте это видно:

В классе этой формы пишем следующее:

SqlConnection con = new SqlConnection("Data Source=(LocalDB)\\MSSQLLocalDB;AttachDbFilename=C:\\Users\\HP\\Desktop\\IOGKF\\IOGKF\\IOGKF_members.mdf;Integrated Security=True;Connect Timeout=30");
SqlCommand cmd;
SqlDataAdapter adapt;

Что-то наподобии этой строчки у вас должно появиться автоматически в Load методе класса вашей формы:

this.membersTableAdapter.Fill(this.iOGKF_membersDataSet.Members);

Она заполняет DataGridView данными из таблицы. Теперь в этот же метод Load добавляем эти строчки кода. С помощью них база данных будет постоянно обновляться внешне:

con.Open();
DataTable dt = new DataTable();
adapt = new SqlDataAdapter("select * from Members", con);
adapt.Fill(dt);
dataGridView1.DataSource = dt;
con.Close();

Готово!

А как сделать так, чтобы каратисты показывались по определённым критериям? Здесь нам нужно делать уже SQL запрос, но о них информация будет чуть позже на канале. Создаём новую форму, добавляем DataGridView и несколько текстовых полей. Кто шарит в SQL, тот поймёт в чем смысл этой формы:

Пишем код в метод, который будет выполняться при нажатии на кнопку "Show":

private void button1_Click(object sender, EventArgs e)
        {
            string SqlText;

            SqlText = "SELECT " + textBox1.Text.ToString() + " FROM Members WHERE " + textBox2.Text.ToString() + " ORDER BY " + textBox3.Text.ToString();

            SqlDataAdapter da = new SqlDataAdapter(SqlText, conString);
            DataSet ds = new DataSet();
            da.Fill(ds, "[Members]");

            dataGridView1.DataSource = ds.Tables["[Members]"].DefaultView;
        }

В принципе, алгоритм здесь тот же самый, но мы уже создаем отдельный DataSet - коллекцию неупорядоченных данных, которые позже будут отображаться в DataGridView. Сам же DataSet был заполнен теми данными, которые получились от SQL запроса.

Форма готова!

Напоследок осталось одно из самых сложных - сделать форму с редактированием базы данных. Вот, как она выглядит:

Как всегда пишем эти строчки кода в класс формы:

public string conString = "Data Source=(LocalDB)\\MSSQLLocalDB;AttachDbFilename=C:\\Users\\HP\\Desktop\\IOGKF\\IOGKF\\IOGKF_members.mdf;Integrated Security=True;Connect Timeout=30";
SqlConnection con = new SqlConnection("Data Source=(LocalDB)\\MSSQLLocalDB;AttachDbFilename=C:\\Users\\HP\\Desktop\\IOGKF\\IOGKF\\IOGKF_members.mdf;Integrated Security=True;Connect Timeout=30");
SqlCommand cmd;
SqlDataAdapter adapt;

А это, как я раньше писал, для постоянного внешнего обновления базы данных в DataGridView:

private void Form7_Load(object sender, EventArgs e)
        {
            this.membersTableAdapter.Fill(this.iOGKF_membersDataSet.Members);
            con.Open();
            DataTable dt = new DataTable();
            adapt = new SqlDataAdapter("select * from Members", con);
            adapt.Fill(dt);
            dataGridView1.DataSource = dt;
            con.Close();
        }

Теперь мы начнём писать код для кнопок.

Код для добавления каратистов из таблицы:

private void button1_Click(object sender, EventArgs e)
        {
            if (textBox1.Text != "" && textBox2.Text != "" && textBox3.Text != "" && textBox4.Text != "" && textBox5.Text != "" && textBox6.Text != "" && textBox7.Text != "" && textBox8.Text != "")
            {
                cmd = new SqlCommand("insert into Members(member_id,last_name,first_name,age,rank,rank_value,sensei,dojo) values(@member_id,@last_name,@first_name,@age,@rank,@rank_value,@sensei,@dojo)", con);
                con.Open();
                cmd.Parameters.AddWithValue("@member_id", textBox1.Text);
                cmd.Parameters.AddWithValue("@last_name", textBox2.Text);
                cmd.Parameters.AddWithValue("@first_name", textBox3.Text);
                cmd.Parameters.AddWithValue("@age", textBox4.Text);
                cmd.Parameters.AddWithValue("@rank", textBox5.Text);
                cmd.Parameters.AddWithValue("@rank_value", textBox6.Text);
                cmd.Parameters.AddWithValue("@sensei", textBox7.Text);
                cmd.Parameters.AddWithValue("@dojo", textBox8.Text);
                cmd.ExecuteNonQuery();
                con.Close();
                MessageBox.Show("Record Inserted Successfully");
                DisplayData();
                ClearData();
            }
            else
            {
                MessageBox.Show("Please Provide Details!");
            }
        }

Код для редактирования информации о каратистах:

private void button4_Click(object sender, EventArgs e)
        {
            if (textBox1.Text != "" && textBox2.Text != "" && textBox3.Text != "" && textBox4.Text != "" && textBox5.Text != "" && textBox6.Text != "" && textBox7.Text != "" && textBox8.Text != "")
            {
                cmd = new SqlCommand("update Members set member_id=@member_id,last_name=@last_name,first_name=@first_name,age=@age,rank=@rank,rank_value=@rank_value,sensei=@sensei,dojo=@dojo where member_id=@member_id", con);
                con.Open();
                cmd.Parameters.AddWithValue("@member_id", textBox1.Text);
                cmd.Parameters.AddWithValue("@last_name", textBox2.Text);
                cmd.Parameters.AddWithValue("@first_name", textBox3.Text);
                cmd.Parameters.AddWithValue("@age", textBox4.Text);
                cmd.Parameters.AddWithValue("@rank", textBox5.Text);
                cmd.Parameters.AddWithValue("@rank_value", textBox6.Text);
                cmd.Parameters.AddWithValue("@sensei", textBox7.Text);
                cmd.Parameters.AddWithValue("@dojo", textBox8.Text);
                cmd.ExecuteNonQuery();
                MessageBox.Show("Record Updated Successfully");
                con.Close();
                DisplayData();
                ClearData();
            }
            else
            {
                MessageBox.Show("Please Select Record to Update");
            }
        }

Код для удаления каратистов из базы данных:

private void button5_Click(object sender, EventArgs e)
        {
            if (textBox1.Text != null)
            {
                cmd = new SqlCommand("delete Members where member_id=@member_id", con);
                con.Open();
                cmd.Parameters.AddWithValue("@member_id", textBox1.Text);
                cmd.ExecuteNonQuery();
                con.Close();
                MessageBox.Show("Record Deleted Successfully!");
                DisplayData();
                ClearData();
            }
            else
            {
                MessageBox.Show("Please Select Record to Delete");
            }
        }

Весь код выше работает по алгоритму, который я объяснял выше: идёт соединение с базой данных, выполняется команда, добавляются параметры в эту команду из текстовых полей и далее выводится сообщение.

Как вы заметили везде вызываются 2 метода - DisplayData и ClearData. Вот код для них:

private void DisplayData()
        {
            con.Open();
            DataTable dt = new DataTable();
            adapt = new SqlDataAdapter("select * from Members", con);
            adapt.Fill(dt);
            dataGridView1.DataSource = dt;
            con.Close();
        }

private void ClearData()
        {
            textBox1.Text = "";
            textBox2.Text = "";
            textBox3.Text = "";
            textBox4.Text = "";
            textBox5.Text = "";
            textBox6.Text = "";
            textBox7.Text = "";
            textBox8.Text = "";
        }

Также надо написать код для метода, который будет вызываться при нажатии на header в DataGridView и будет заполнять текстовые поля. Header - эта та область DataGridView, при нажатии на которую будет выделяться вся информация о каратисте, соответственно эта информация будет добавляться в соответствующие текстовые поля, для удобного редактирования. Выглядит это так:

Но прежде чем добавить этот метод, нам необходимо создать обработчик нажатий (Event Handler). Добавляем его в конструктор нашей формы:

public Form7()
        {
            InitializeComponent();
            dataGridView1.RowHeaderMouseClick += new DataGridViewCellMouseEventHandler(OnRowHeaderMouseClick);
        }

А вот теперь добавляем метод:

private void OnRowHeaderMouseClick(object sender, DataGridViewCellMouseEventArgs e)
        {
            textBox1.Text = dataGridView1.Rows[e.RowIndex].Cells[0].Value.ToString();
            textBox2.Text = dataGridView1.Rows[e.RowIndex].Cells[1].Value.ToString();
            textBox3.Text = dataGridView1.Rows[e.RowIndex].Cells[2].Value.ToString();
            textBox4.Text = dataGridView1.Rows[e.RowIndex].Cells[3].Value.ToString();
            textBox5.Text = dataGridView1.Rows[e.RowIndex].Cells[4].Value.ToString();
            textBox6.Text = dataGridView1.Rows[e.RowIndex].Cells[5].Value.ToString();
            textBox7.Text = dataGridView1.Rows[e.RowIndex].Cells[6].Value.ToString();
            textBox8.Text = dataGridView1.Rows[e.RowIndex].Cells[7].Value.ToString();
        }

Вот и всё! У нас почти готовая программа, тебе надо лишь чуть доработать её и добавить мелкие детали!


Если что, я добавил этот проект к себе в GitHub, поэтому весь код можно посмотреть именно там. Только осторожно, там очень много файлов в которых можно легко запутаться. Желаю тебе удачи! :D

Мой GitHub

Есть вопросы? Пиши @coders_assistant_bot.