a MySQL SQL statement More...
#include <mysqlpl.h>

Public Member Functions | |
| SqlStatement (MSqlConnection &conn) | |
| SqlStatement (MSqlConnection &conn, const std::string &sql) | |
| SqlStatement (MSqlConnection &conn, const SqlQuery &query) | |
| ~SqlStatement () | |
| void | prepare (const std::string &sql) | 
| const std::string & | get_last_sql () const | 
| LONGLONG | get_row_count () const | 
| void | bind_param (int idx, BindPar par) | 
| void | bind_params (const BindVector ¶ms) | 
| void | execute () | 
| void | execute (const std::string &sql) | 
| void | execute (const SqlQuery &query) | 
| bool | execute_fetch () | 
| bool | execute_fetch (const std::string &sql) | 
| bool | fetch () | 
| MYSQL_RES * | get_meta_res () const | 
| bool | is_select () const | 
| int | get_column_count () const | 
| void | get_column_type (int idx, ColumnType &info) const | 
| void | print_results (std::ostream &out, bool header=true) | 
| void | print_results (const std::string &sql, std::ostream &out, bool header=true) | 
| SqlResult * | operator-> () | 
Protected Types | |
| enum | STATE { UNINITIALIZED = 0, EXECUTED = 4, FETCHED = 8 } | 
Protected Member Functions | |
| std::string | create_bound_sql () const | 
Protected Attributes | |
| MYSQL * | _db | 
| std::string | _sql | 
| BindVector | _param_bind_vector | 
| MYSQL_RES * | _result | 
| int | _state | 
| std::string | _last_sql | 
| struct SqlResult * | _res | 
| int | _stmt_type | 
a MySQL SQL statement
Definition at line 1217 of file mysqlpl.h.
enum MySqlPL::SqlStatement::STATE [protected] | 
        
Definition at line 1244 of file mysqlpl.h.
               {
        UNINITIALIZED=0,
#if MYSQLPL_PREP_STMT
        PREPARED=1, RESULT_BOUND=2,
#endif
        EXECUTED=4, FETCHED=8,
        //EOF_DATA=16, STMT_ERROR=32
    };
| MySqlPL::SqlStatement::SqlStatement | ( | MSqlConnection & | conn ) | 
Definition at line 485 of file mysqlpl.cpp.
References _db.
: _db(conn), _state(UNINITIALIZED), _res(NULL), _stmt_type(-1), _result(NULL) { #if MYSQLPL_PREP_STMT _stmt = mysql_stmt_init(_db); #endif }
| MySqlPL::SqlStatement::SqlStatement | ( | MSqlConnection & | conn, | 
| const std::string & | sql | ||
| ) | 
Definition at line 497 of file mysqlpl.cpp.
References _db, and prepare().
: _db(conn), _state(UNINITIALIZED), _res(NULL), _stmt_type(-1), _result(NULL) { #if MYSQLPL_PREP_STMT _stmt = mysql_stmt_init(_db); #endif prepare(sql); }

| MySqlPL::SqlStatement::SqlStatement | ( | MSqlConnection & | conn, | 
| const SqlQuery & | query | ||
| ) | 
Definition at line 511 of file mysqlpl.cpp.
References _db, and execute().
: _db(conn), _state(UNINITIALIZED), _res(NULL), _stmt_type(-1), _result(NULL) { #if MYSQLPL_PREP_STMT _stmt = mysql_stmt_init(_db); #endif execute(query); }

| MySqlPL::SqlStatement::~SqlStatement | ( | ) | 
Definition at line 525 of file mysqlpl.cpp.
References _result.
| void MySqlPL::SqlStatement::bind_param | ( | int | idx, | 
| BindPar | par | ||
| ) | 
Definition at line 812 of file mysqlpl.cpp.
References _param_bind_vector, and MySqlPL::BindVector::bind().
{
    if ((int)_param_bind_vector.size() <= idx)
        _param_bind_vector.resize(idx+1);
    _param_bind_vector.bind(idx, par);
}

| void MySqlPL::SqlStatement::bind_params | ( | const BindVector & | params ) |  [inline] | 
        
Definition at line 1288 of file mysqlpl.h.
References _param_bind_vector.
Referenced by execute().
    {
        _param_bind_vector = params;
    }

| std::string MySqlPL::SqlStatement::create_bound_sql | ( | ) |  const [protected] | 
        
Definition at line 680 of file mysqlpl.cpp.
References MySqlPL::BindPar::_len, _param_bind_vector, MySqlPL::BindPar::_ptr, _sql, MySqlPL::BindPar::_type, MYSQL_TYPE_DOUBLE, MYSQL_TYPE_LONG, MYSQL_TYPE_VAR_STRING, MySqlPL::next_bind_variable(), and THROW_MYSQLPL_EXCEPTION.
Referenced by execute().
{
    const char* p = _sql.c_str();
    std::string sql;
    char buffer[64];
    for(BindVector::const_iterator it=_param_bind_vector.begin(); it!=_param_bind_vector.end(); ++it) {
        const char* q = next_bind_variable(p);
        if (!q)
            THROW_MYSQLPL_EXCEPTION("too much bind values");
        sql.append(p, q-p);
        const BindPar& value = *it;
        switch(value._type) {
          case MYSQL_TYPE_VAR_STRING: {
            sql.append("'");
             // escape quote characters in bound string constants
            const char* p = (const char*)value._ptr;
            for(int i=0; i<value._len; ++i,++p)
                if (*p == '\'')
                    sql.append("''");
                else
                    sql.append(p, 1);
            sql.append("'");
            break;}
          case MYSQL_TYPE_LONG:
            sql.append(buffer, sprintf(buffer,"%d",*(int*)value._ptr));
            break;
          case MYSQL_TYPE_DOUBLE:
            sql.append(buffer, sprintf(buffer,"%f",*(double*)value._ptr));
            break;
          default:
            THROW_MYSQLPL_EXCEPTION("unsupported datatype");
        }
        p = q + 1;
    }
    if (next_bind_variable(p))
        THROW_MYSQLPL_EXCEPTION("too less bind values");
    sql.append(p);
    return sql;
}    


| void MySqlPL::SqlStatement::execute | ( | const std::string & | sql ) |  [inline] | 
        
| void MySqlPL::SqlStatement::execute | ( | const SqlQuery & | query ) |  [inline] | 
        
Definition at line 1316 of file mysqlpl.h.
References bind_params(), execute(), MySqlPL::SqlQuery::get_params(), MySqlPL::SqlQuery::get_sql(), and prepare().
    {
        prepare(query.get_sql());
        bind_params(query.get_params());
        execute();
    }

| void MySqlPL::SqlStatement::execute | ( | ) | 
Definition at line 608 of file mysqlpl.cpp.
References _db, _param_bind_vector, _res, _result, _state, create_bound_sql(), EXECUTED, FETCHED, get_column_count(), is_select(), and MySqlPL::mysqlpl_check_error().
Referenced by MySqlPL::MSqlConnection::connect(), execute(), execute_fetch(), fetch(), print_results(), and SqlStatement().
{
#if MYSQLPL_PREP_STMT
    if (!(_state & RESULT_BOUND)) {
         // a SELECT statement without ready define variables?
        if (is_select()) {  // a statement with result set? (=> SELECT)
            _result_bind_vector.resize(get_column_count());
             // define resultset variables
            assert(!_res);
            _res = new SqlResult(*this);
        }
    }
    MSqlBindVector param_mbind_vector;
     // bind parameter values
    if (!_param_bind_vector.empty()) {
         // Umwandlung der Bindparameter von BindPar in MYSQL_BIND-Strukturelemente
        param_mbind_vector.resize(_param_bind_vector.size());
        MSqlBindVector::iterator out = param_mbind_vector.begin();
        for(BindVector::const_iterator in=_param_bind_vector.begin(); in!=_param_bind_vector.end(); ++in,++out)
            mysql_bind_param(*in, *out);
        my_bool res = mysql_stmt_bind_param(_stmt, ¶m_mbind_vector[0]);
        mysqlpl_check_error(_stmt, res);
    }
    int res = mysql_stmt_execute(_stmt);
    mysqlpl_check_error(_stmt, res);
#else
    int res = mysql_query(_db, create_bound_sql().c_str());
    mysqlpl_check_error(_db, res);
    if (_result)
        mysql_free_result(_result);
    _result = mysql_store_result(_db);
    if (_result) { // is_select()
         // define resultset variables
        if (_res)
            delete _res;
        _res = new SqlResult(*this);
    }
#endif
    _state = (_state|EXECUTED) & ~FETCHED;
}


| bool MySqlPL::SqlStatement::execute_fetch | ( | ) |  [inline] | 
        
| bool MySqlPL::SqlStatement::execute_fetch | ( | const std::string & | sql ) |  [inline] | 
        
Definition at line 1330 of file mysqlpl.h.
References execute_fetch(), and prepare().
    {
        prepare(sql);
        return execute_fetch();
    }

| bool MySqlPL::SqlStatement::fetch | ( | ) |  [inline] | 
        
Definition at line 1337 of file mysqlpl.h.
References _res, _result, MySqlPL::SqlResult::_row, _state, execute(), EXECUTED, FETCHED, and MySqlPL::mysqlpl_check_error().
Referenced by execute_fetch(), operator->(), and print_results().
    {
        if (!(_state & EXECUTED))
            execute();
#if MYSQLPL_PREP_STMT
        int res = mysql_stmt_fetch(_stmt);
        if (res == MYSQL_NO_DATA)
            return false;
        mysqlpl_check_error(_stmt, res);
#else
        _res->_row = mysql_fetch_row(_result);
        if (!_res->_row)
            return false;
#endif
        _state |= FETCHED;
        return true;
    }


| int MySqlPL::SqlStatement::get_column_count | ( | ) | const | 
Definition at line 767 of file mysqlpl.cpp.
References _result, get_meta_res(), and THROW_MYSQLPL_EXCEPTION.
Referenced by execute(), and MySqlPL::SqlRecord::SqlRecord().
{
#if MYSQLPL_PREP_STMT
    unsigned count = mysql_num_fields(get_meta_res());
    if (count == (unsigned)-1)
        THROW_MYSQLPL_EXCEPTION(_stmt);
    return count;
#else
    return mysql_num_fields(_result);
#endif
}


| void MySqlPL::SqlStatement::get_column_type | ( | int | idx, | 
| ColumnType & | info | ||
| ) | const | 
Definition at line 781 of file mysqlpl.cpp.
References _db, get_meta_res(), MySqlPL::ColumnType::init(), and THROW_MYSQLPL_EXCEPTION.
{
    MYSQL_FIELD* field = mysql_fetch_field_direct(get_meta_res(), idx);
    if (!field)
#if MYSQLPL_PREP_STMT
        THROW_MYSQLPL_EXCEPTION(_stmt);
#else
        THROW_MYSQLPL_EXCEPTION(_db);
#endif
    info.init(field);
}

| const std::string& MySqlPL::SqlStatement::get_last_sql | ( | ) |  const [inline] | 
        
| MYSQL_RES * MySqlPL::SqlStatement::get_meta_res | ( | ) | const | 
Definition at line 737 of file mysqlpl.cpp.
References _result, and THROW_MYSQLPL_EXCEPTION.
Referenced by get_column_count(), get_column_type(), and MySqlPL::SqlRecord::SqlRecord().
{
#if MYSQLPL_PREP_STMT
    if (!_result) {
        _result = mysql_stmt_result_metadata(_stmt);
        if (!_result)
            THROW_MYSQLPL_EXCEPTION("no result set metadata");
    }
#endif
    return _result;
}

| LONGLONG MySqlPL::SqlStatement::get_row_count | ( | ) | const | 
Definition at line 563 of file mysqlpl.cpp.
References _db, is_select(), LONGLONG, and THROW_MYSQLPL_EXCEPTION.
{
#if MYSQLPL_PREP_STMT
    if (is_select()) {
        if (mysql_stmt_store_result(_stmt))
            THROW_MYSQLPL_EXCEPTION(_stmt);
    }
    LONGLONG res = mysql_stmt_affected_rows(_stmt); // for DML statements
/*
    if (res == -1)
        res = mysql_stmt_num_rows(_stmt);   // only for SELECT statements
*/
    if (res == -1)
        THROW_MYSQLPL_EXCEPTION(_stmt);
#else
    int res = mysql_affected_rows(_db);
    if (res == -1)
        THROW_MYSQLPL_EXCEPTION(_db);
#endif
    return res;
}

| bool MySqlPL::SqlStatement::is_select | ( | ) | const | 
Definition at line 751 of file mysqlpl.cpp.
References _result, _state, EXECUTED, and THROW_MYSQLPL_EXCEPTION.
Referenced by execute(), and get_row_count().
{
#if MYSQLPL_PREP_STMT
    if (!_result)
        _result = mysql_stmt_result_metadata(_stmt);
    return _result!=NULL;
#else
    if (!(_state & EXECUTED))
        THROW_MYSQLPL_EXCEPTION("statement not yet executed");
    return _result!=NULL;
#endif
}

| SqlResult* MySqlPL::SqlStatement::operator-> | ( | ) |  [inline] | 
        
| void MySqlPL::SqlStatement::prepare | ( | const std::string & | sql ) | 
Definition at line 537 of file mysqlpl.cpp.
References _last_sql, _param_bind_vector, _res, _result, _sql, _state, _stmt_type, and MySqlPL::mysqlpl_check_error().
Referenced by execute(), execute_fetch(), and SqlStatement().
{
    delete _res;
    _res = NULL;
    _last_sql = sql;
#if MYSQLPL_PREP_STMT
    int res = mysql_stmt_prepare(_stmt, sql.c_str(), sql.length());
    mysqlpl_check_error(_stmt, res);
    _state = PREPARED;
#else
    _sql = sql;
    if (_result)
        mysql_free_result(_result);
#endif
    _stmt_type = -1;
    _result = NULL;
//  _result_bind_vector.clear();
    _param_bind_vector.clear();
}


| void MySqlPL::SqlStatement::print_results | ( | std::ostream & | out, | 
| bool |  header = true  | 
        ||
| ) | 
Definition at line 837 of file mysqlpl.cpp.
References _res, _state, execute(), EXECUTED, fetch(), MySqlPL::SqlRecord::print_columns(), and MySqlPL::SqlRecord::print_values().
Referenced by print_results().
{
    if (!(_state & EXECUTED))
        execute();
    if (header)
        _res->print_columns(out);
    int row_cnt = 0;
    while(fetch()) {
        ++row_cnt;
        out << "row " << row_cnt << ":\n";
        _res->print_values(out);
        out << std::endl;
    }
}


| void MySqlPL::SqlStatement::print_results | ( | const std::string & | sql, | 
| std::ostream & | out, | ||
| bool |  header = true  | 
        ||
| ) |  [inline] | 
        
Definition at line 1371 of file mysqlpl.h.
References execute(), and print_results().
    {
        execute(sql);
        print_results(out, header);
    }

MYSQL* MySqlPL::SqlStatement::_db [protected] | 
        
Definition at line 1228 of file mysqlpl.h.
Referenced by execute(), get_column_type(), get_row_count(), and SqlStatement().
std::string MySqlPL::SqlStatement::_last_sql [protected] | 
        
Definition at line 1254 of file mysqlpl.h.
Referenced by get_last_sql(), and prepare().
BindVector MySqlPL::SqlStatement::_param_bind_vector [protected] | 
        
Definition at line 1240 of file mysqlpl.h.
Referenced by bind_param(), bind_params(), create_bound_sql(), execute(), and prepare().
struct SqlResult* MySqlPL::SqlStatement::_res [protected] | 
        
Definition at line 1256 of file mysqlpl.h.
Referenced by execute(), fetch(), operator->(), prepare(), and print_results().
MYSQL_RES* MySqlPL::SqlStatement::_result [mutable, protected] | 
        
Definition at line 1242 of file mysqlpl.h.
Referenced by execute(), fetch(), get_column_count(), get_meta_res(), is_select(), prepare(), and ~SqlStatement().
std::string MySqlPL::SqlStatement::_sql [protected] | 
        
Definition at line 1235 of file mysqlpl.h.
Referenced by create_bound_sql(), and prepare().
int MySqlPL::SqlStatement::_state [protected] | 
        
Definition at line 1252 of file mysqlpl.h.
Referenced by execute(), fetch(), is_select(), prepare(), and print_results().
int MySqlPL::SqlStatement::_stmt_type [protected] | 
        
 1.7.2