badc428423c6d92d53c14749016537f4e880c3ab..cec6937344e179a6db50c6386b24afcff165561f
2025-04-02 zyf
zyf_0402_log
cec693 对比 | 目录
2025-03-20 zyf
.h&.cpp文件
6cc7dc 对比 | 目录
2025-03-20 zyf
数据库相关代码
f692a8 对比 | 目录
2025-03-20 zyf
关于数据库代码
67c2d1 对比 | 目录
5个文件已添加
1个文件已删除
455 ■■■■■ 已修改文件
Server/张怡帆/code/ConnectMysql.cpp 300 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
Server/张怡帆/code/ConnectMysql.h 61 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
Server/张怡帆/code/Database_Package.cpp 94 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
Server/张怡帆/log/~WRL1218.tmp 补丁 | 查看 | 原始文档 | blame | 历史
Server/张怡帆/log/~WRL1951.tmp 补丁 | 查看 | 原始文档 | blame | 历史
Server/张怡帆/log/日志_张怡帆_250402.doc 补丁 | 查看 | 原始文档 | blame | 历史
Server/ÕÅâù·«/code/ConnectMysql.cpp
New file
@@ -0,0 +1,300 @@
#include "ConnectMysql.h"
// æž„造函数实现,初始化成员变量
ConnectMysql::ConnectMysql()
{
    m_result = nullptr;
    m_mysqlRow = nullptr;
    m_conn = mysql_init(nullptr);    // åˆå§‹åŒ–MySQL连接对象,传入nullptr会自动分配一个MYSQL对象
    if (m_conn == nullptr)
    {
        cout << "初始化失败" << endl;
        return;
    }
    cout << "初始化成功" << endl;
}
// æžæž„函数实现,释放结果集和数据库连接资源
ConnectMysql::~ConnectMysql()
{
    freeRes();// é‡Šæ”¾ç»“果集
    if (m_conn != nullptr) {
        mysql_close(m_conn);
        m_conn = nullptr;
        cout << "数据库连接关闭" << endl;
    }
}
// é‡Šæ”¾ç»“果集资源的函数实现
void ConnectMysql::freeRes()
{
    if (m_result) {
        mysql_free_result(m_result);
        m_result = nullptr;
    }
}
// ä½¿ç”¨ Shell è„šæœ¬å¤‡ä»½æ•°æ®åº“
void ConnectMysql::backupCurrentDBUsingShell(const string path)
{
    string user = "root";
    string passwd = "1";
    string dbName = "AI_datas";
    string command = "sh backup_script.sh " + user + " " + passwd + " " + dbName + " " + path;
    int result = system(command.c_str());
    if (result != 0) {
        cerr << "备份失败!" << endl;//cerr: è¿™æ˜¯ä¸€ä¸ªæ ‡å‡†è¾“出流,用于输出错误信息.
    }
}
// è¿žæŽ¥æ•°æ®åº“的函数实现
bool ConnectMysql::connect(const string user, const string passwd,
    const string dbName, string ip, const unsigned short port)
{
    MYSQL* res = mysql_real_connect(m_conn, ip.c_str(), user.c_str(),
        passwd.c_str(), dbName.c_str(), port, nullptr, 0);    // ä½¿ç”¨mysql_real_connect连接数据库
    if (res == nullptr)
    {
        cout << "数据库连接失败" << endl;
        return false;
    }
    cout << "数据库连接成功" << endl;
    if (mysql_set_character_set(m_conn, "GBK")) {// è®¾ç½®å­—符集,防止乱码
        puts("字符集设置错误!");
    }
    else {
        puts("字符集设置成功!");
    }
    return res != nullptr;
}
// æ‰§è¡Œæ›´æ–°æ“ä½œï¼ˆå¢žåˆ æ”¹ï¼‰çš„函数实现
bool ConnectMysql::update(const string sql) const
{
    // æ‰§è¡ŒSQL语句,成功返回0,失败返回非0值
    int res = mysql_real_query(m_conn, sql.c_str(), static_cast<unsigned int>(sql.size()));
    if (res != 0) {
        return false;
    }
    return true;
}
// æ‰§è¡ŒæŸ¥è¯¢æ“ä½œçš„函数实现
bool ConnectMysql::query(const string sql)
{
    freeRes();// é‡Šæ”¾ç»“果集
    int res = mysql_real_query(m_conn, sql.c_str(), static_cast<unsigned int>(sql.size()));    // æ‰§è¡ŒæŸ¥è¯¢SQL语句
    if (res != 0) {
        cout << "查询失败" << endl;
        return false;
    }
    // èŽ·å–æŸ¥è¯¢ç»“æžœé›†
    m_result = mysql_store_result(m_conn);
    if (m_result == nullptr) {
        cout << "查询失败" << endl;
        return false;
    }
    return true;
}
// éåŽ†æŸ¥è¯¢ç»“æžœé›†çš„å‡½æ•°å®žçŽ°
bool ConnectMysql::getRes()
{
    if (m_result != nullptr) {
        // èŽ·å–ç»“æžœé›†ä¸­çš„ä¸‹ä¸€è¡Œæ•°æ®
        m_mysqlRow = mysql_fetch_row(m_result);
        if (m_mysqlRow != nullptr) {
            return true;
        }
        freeRes();
    }
    return false;
}
// èŽ·å–ç»“æžœé›†ä¸­æŒ‡å®šå­—æ®µå€¼çš„å‡½æ•°å®žçŽ°
string ConnectMysql::getValue(const int fieldIndex) const//fieldIndex:字段索引
{
    // èŽ·å–ç»“æžœé›†ä¸­çš„å­—æ®µæ•°é‡
    int fieldCount = mysql_num_fields(m_result);
    if (fieldIndex >= fieldCount || fieldIndex < 0) {
        return string();// è¿”回空字符串
    }
    // èŽ·å–æŒ‡å®šå­—æ®µçš„å€¼
    char* value = m_mysqlRow[fieldIndex];
    // èŽ·å–å„å­—æ®µå€¼çš„é•¿åº¦æ•°ç»„
    unsigned long* len = mysql_fetch_lengths(m_result);// mysql_fetch_lengths:获取所有字段值的长度
    unsigned long length = len[fieldIndex];
    // é˜²æ­¢æ•°æ®ä¸­å­˜åœ¨\0导致数据丢失,使用指定长度构造字符串
    return string(value, length);
}
// èŽ·å–æŸ¥è¯¢ç»“æžœé›†çš„å‡½æ•°å®žçŽ°
vector<vector<string>> ConnectMysql::getQueryResults()
{
    vector<vector<string>> results;
    if (m_result != nullptr)
    {
        int num_fields = mysql_num_fields(m_result);
        while ((m_mysqlRow = mysql_fetch_row(m_result)))
        {
            vector<string> row;//vector<string> ä»£è¡¨ä¸€è¡ŒæŸ¥è¯¢ç»“æžœ
            for (int i = 0; i < num_fields; ++i)
            {
                if (m_mysqlRow[i] != nullptr)
                {
                    row.push_back(m_mysqlRow[i]);
                }
                else
                {
                    row.push_back("");  // å¤„理 NULL å€¼
                }
            }
            results.push_back(row);
        }
    }
    return results;
}
//// åˆ‡æ¢æ•°æ®åº“的函数实现
//bool ConnectMysql::selectDB(const string dbName) const
//{
//    // æ‰§è¡Œåˆ‡æ¢æ•°æ®åº“的操作
//    int res = mysql_select_db(m_conn, dbName.c_str());
//    if (res != 0) {
//        return false;
//    }
//    return true;
//}
//// åˆ›å»ºæ•°æ®åº“的函数实现
//bool ConnectMysql::createDB(const string dbName) const
//{
//    // æ‹¼æŽ¥åˆ›å»ºæ•°æ®åº“çš„SQL语句
//    string sql = "create database " + dbName + ";";
//    // æ‰§è¡Œåˆ›å»ºæ•°æ®åº“çš„SQL语句
//    int res = mysql_real_query(m_conn, sql.c_str(), static_cast<unsigned long>(sql.size()));
//    if (res != 0) {
//        return false;
//    }
//    return true;
//}
// å¤‡ä»½å½“前数据库的函数实现
void ConnectMysql::backupCurrentDB(const string path)
{
    // æŸ¥è¯¢å½“前数据库中的所有表
    string sql = "show tables";
    int r = mysql_real_query(m_conn, sql.c_str(), static_cast<unsigned long>(sql.size()));
    if (r != 0) {
        return;
    }
    // èŽ·å–æŸ¥è¯¢ç»“æžœé›†
    MYSQL_RES* tableRes = mysql_store_result(m_conn);
    for (int i = 0; i < mysql_num_rows(tableRes); ++i) {
        // èŽ·å–è¡¨å
        MYSQL_ROW tableName = mysql_fetch_row(tableRes);
        // å¤‡ä»½æ¯ä¸ªè¡¨
        backupCurrentTable(path, tableName[0]);
    }
}
// å¤‡ä»½å½“前表的函数实现
void ConnectMysql::backupCurrentTable(const string path, const string tableName)
{
    // æ‹¼æŽ¥å¤‡ä»½è¡¨çš„æ–‡ä»¶å
    string file = path + tableName + ".sql";
    // æ‰“开文件用于写入
    ofstream ofs(file);
    if (!ofs.is_open()) {
        cout << "文件打开失败!" << endl;
        return;
    }
    // å†™å…¥è¡¨ç»“æž„
    string showCreate = "show create table " + tableName + ";";//show create table: æŸ¥çœ‹è¡¨ç»“æž„
    bool res = query(showCreate);
    if (!res) {
        return;
    }
    if (getRes()) {
        string writeSQL = getValue(1) + ";\n";
        ofs.write(writeSQL.c_str(), writeSQL.size());
    }
    // å†™å…¥è¡¨æ•°æ®
    string sql = "select * from " + tableName + ";";
    res = query(sql);
    if (!res) {
        return;
    }
    while (getRes()) {
        string writeSQL = "insert into `" + tableName + "` values(";
        for (int i = 0; !getValue(i).empty(); ++i) {
            if (i != 0) {
                writeSQL += ",";
            }
            // èŽ·å–å­—æ®µç±»åž‹
            MYSQL_FIELD* valueType = mysql_fetch_field_direct(m_result, i);//获取当前列的字段信息。根据字段类型判断是否需要加引号
            if (valueType->type == MYSQL_TYPE_DECIMAL
                || valueType->type == MYSQL_TYPE_TINY
                || valueType->type == MYSQL_TYPE_SHORT
                || valueType->type == MYSQL_TYPE_LONG
                || valueType->type == MYSQL_TYPE_FLOAT
                || valueType->type == MYSQL_TYPE_DOUBLE
                || valueType->type == MYSQL_TYPE_TIMESTAMP
                || valueType->type == MYSQL_TYPE_LONGLONG
                || valueType->type == MYSQL_TYPE_INT24
                || valueType->type == MYSQL_TYPE_BOOL) {//小数,整数,浮点数,时间,长整数,短整数,布尔值
                writeSQL += getValue(i);
            }
            else {
                writeSQL += "'" + getValue(i) + "'";
            }
        }
        writeSQL += ");\n";
        ofs.write(writeSQL.c_str(), writeSQL.size());
    }
    ofs.close();
}
// å¼€å¯äº‹åŠ¡çš„å‡½æ•°å®žçŽ°
bool ConnectMysql::transaction() const
{
    // å°†äº‹åŠ¡æäº¤è®¾ç½®ä¸ºæ‰‹åŠ¨æäº¤ï¼Œå¼€å¯äº‹åŠ¡
    return mysql_autocommit(m_conn, false);
}
// æäº¤äº‹åŠ¡çš„å‡½æ•°å®žçŽ°
bool ConnectMysql::commit() const
{
    // æäº¤äº‹åŠ¡
    return mysql_commit(m_conn);
}
// å›žæ»šäº‹åŠ¡çš„å‡½æ•°å®žçŽ°
bool ConnectMysql::rollback() const
{
    // å›žæ»šäº‹åŠ¡
    return mysql_rollback(m_conn);
}
// åˆ·æ–°è¿žæŽ¥å­˜æ´»èµ·å§‹æ—¶é—´ç‚¹çš„函数实现
void ConnectMysql::refreashAliveTime()
{
    // æ›´æ–°è¿žæŽ¥å­˜æ´»èµ·å§‹æ—¶é—´ç‚¹
    m_alivetime = std::chrono::steady_clock::now();// èŽ·å–å½“å‰æ—¶é—´ç‚¹
}
// èŽ·å–è¿žæŽ¥å­˜æ´»æ—¶é•¿çš„å‡½æ•°å®žçŽ°
ll ConnectMysql::getAliveTime()
{
    // è®¡ç®—连接存活时长,转换为毫秒
    auto now = std::chrono::steady_clock::now();
    std::chrono::duration<long long, std::milli> res = std::chrono::duration_cast<std::chrono::milliseconds>(now - m_alivetime);
    return res.count();
}
Server/ÕÅâù·«/code/ConnectMysql.h
New file
@@ -0,0 +1,61 @@
#include <iostream>
//#include <mysql.h>
#include <winsock2.h>
#include "mysql/include/mysql.h"
#include <memory>
#include <string>
#include <chrono>
#include <fstream>
#include <vector>
using namespace std;
#pragma comment(lib, "libmysql.lib")
#pragma comment(lib, "ws2_32.lib")
typedef long long ll;
/*
mysql_init() åˆå§‹åŒ–MYSQL变量
mysql_real_connect //连接到数据库
mysql_real_query //数据库查询
mysql_query(MYSQL*mysql,const char*query)
mysql_store_result/mysql_use_result //返回的获取查询结果数据
mysql_fetch_row//读取结果集数据
mysql_free_result//释放结果集,以防内存泄漏
mysql_close//关闭数据库连接
*/
class ConnectMysql
{
private:
    std::chrono::steady_clock::time_point m_alivetime;// è®°å½•连接的存活起始时间点
    MYSQL* m_conn;
    MYSQL_RES* m_result;// ä¿å­˜æŸ¥è¯¢ç»“æžœ
    MYSQL_ROW m_mysqlRow;// ä¿å­˜æŸ¥è¯¢ç»“果的某一行
    void freeRes();// é‡Šæ”¾ç»“果集
public:
    ConnectMysql();
    ~ConnectMysql();
    bool connect(const string user = "root", const string passwd = "1",
        const string dbName = "AI_datas", string ip = "192.168.133.129", const unsigned short port = 3306);// è¿žæŽ¥æ•°æ®åº“
    bool update(const string sql) const;// æ›´æ–°æ•°æ®åº“
    bool query(const string sql);// æŸ¥è¯¢æ•°æ®åº“
    bool getRes();// éåŽ†æŸ¥è¯¢ç»“æžœé›†ï¼ŒèŽ·å–ä¸‹ä¸€è¡Œæ•°æ®
    string getValue(const int fieldIndex) const;// èŽ·å–æŸ¥è¯¢ç»“æžœé›†æŸä¸€è¡Œçš„æŸä¸€åˆ—
    vector<vector<string>> getQueryResults();  // æŸ¥è¯¢ç»“æžœ
    //bool selectDB(const string dbName) const;// é€‰æ‹©æ•°æ®åº“
    //bool createDB(const string dbName) const;// åˆ›å»ºæ•°æ®åº“
    void backupCurrentDBUsingShell(const string path);    // ä½¿ç”¨ Shell è„šæœ¬å¤‡ä»½æ•°æ®åº“
    void backupCurrentDB(const string path);    //备份数据库
    void backupCurrentTable(const string path, const string tableName);
    bool transaction() const;// å¼€å¯äº‹åŠ¡
    bool commit() const;// æäº¤äº‹åŠ¡
    bool rollback() const;// å›žæ»šäº‹åŠ¡
    void refreashAliveTime();// åˆ·æ–°å­˜æ´»æ—¶é—´
    ll getAliveTime();// èŽ·å–å­˜æ´»æ—¶é—´ï¼Œå•ä½ï¼šæ¯«ç§’
};
Server/ÕÅâù·«/code/Database_Package.cpp
New file
@@ -0,0 +1,94 @@
// Database_Package.cpp : æ­¤æ–‡ä»¶åŒ…含 "main" å‡½æ•°ã€‚程序执行将在此处开始并结束。
//
#include <iostream>
//#include <mysql.h>
#include <winsock2.h>
#include "mysql/include/mysql.h"
#include <memory>
#include <string>
#include <chrono>
#include <fstream>
#include "ConnectionPool.h"
using namespace std;
/*
#define M_MYSQL_DNAME AI_datas
#define M_MYSQL_IP 192.168.133.129
#define M_MYSQL_PORT 3306
#define M_MYSQL_USER root
#define M_MYSQL_PASSWD 1
#define M_MYSQL_PATH D:\\PROGECT_0214
*/
void testDatabaseConnection()
{
    // åˆ›å»ºè¿žæŽ¥æ± å¯¹è±¡
    ConnectionPool* pool = ConnectionPool::getInstance();
    // ä»Žè¿žæŽ¥æ± ä¸­èŽ·å–è¿žæŽ¥
    shared_ptr<ConnectMysql> conn = pool->getConnection();
    if (conn == nullptr)
    {
        cerr << "未取得数据库连接!" << endl;
        return;
    }
    cout << "连接成功" << endl;
    // æµ‹è¯•更新功能
    string sql = "INSERT INTO employee_info (employee_name, employee_age, employee_sex, employee_bir, employee_password, employee_email, employee_phone, employee_department)VALUES('朱琛', 20, '男', '1999-09-09', '123456', '123456@123.com', '12345678901', 'asdf')";
    if (conn->update(sql))
    {
        cout << "更新成功!" << endl;
    }
    else
    {
        cerr << "更新失败!" << endl;
    }
    // æµ‹è¯•查询功能
    sql = "SELECT * FROM employee_info";
    if (conn->query(sql))
    {
        cout << "正在查询..." << endl;
        // èŽ·å–æŸ¥è¯¢ç»“æžœ
        vector<vector<string>> results = conn->getQueryResults();
        // å¤„理查询结果
        for (const auto& row : results)
        {
            for (const auto& field : row)
            {
                cout << field << "\t";
            }
            cout << endl;
        }
    }
    else
    {
        cerr << "查询失败!" << endl;
    }
    // å®žçŽ°å¤‡ä»½åŠŸèƒ½
    string backupPath = "D:\\PROGECT_0214\\";  // å¤‡ä»½è·¯å¾„,你可以根据需要修改
    cout << "开始备份数据库..." << endl;
    conn->backupCurrentDB(backupPath);
    cout << "数据库备份完成!" << endl;
    cout << "开始备份表 employee_info..." << endl;
    conn->backupCurrentTable(backupPath, "employee_info");
    cout << "表 employee_info å¤‡ä»½å®Œæˆï¼" << endl;
    // ä½¿ç”¨shell脚本备份数据库
//string backupPath = "D:\\PROGECT_0214\\";  // å¤‡ä»½è·¯å¾„,你可以根据需要修改
//cout << "开始使用shell脚本备份数据库..." << endl;
//conn->backupCurrentDBUsingShell(backupPath);
//cout << "数据库备份完成!" << endl;
}
int main()
{
    testDatabaseConnection();
    return 0;
}
Server/ÕÅâù·«/log/~WRL1218.tmp
Binary files differ
Server/ÕÅâù·«/log/~WRL1951.tmp
Binary files differ
Server/ÕÅâù·«/log/ÈÕÖ¾_ÕÅâù·«_250402.doc
Binary files differ