Boost logo

Boost Users :

Subject: Re: [Boost-users] [boost::system] Is the library abstraction general enough?
From: Emil Dotchevski (emildotchevski_at_[hidden])
Date: 2009-02-23 12:36:35


On Mon, Feb 23, 2009 at 2:33 AM, Lian Cheng <rhythm.mail_at_[hidden]> wrote:
> Boris Schaeling:
>>
>> On Fri, 20 Feb 2009 09:36:53 +0100, Lian Cheng <rhythm.mail_at_[hidden]>
>> wrote:
>>
>> Isn't there a list of error numbers and error strings MySQL uses? I ask as
>> calling error_category::message() should also return an error string even if
>> no MySQL connection is used?
>
> Unfortunately, no. As I've mentioned, the error strings MySQL uses are
> printf format strings, such as:
>
> Using unsupported buffer type: %d (parameter: %d)
>
> And you always need an active MySQL connection handle to obtain the full
> error message by calling mysql_error(). And you can never get the message
> back once you close the connection:
>
> MYSQL* conn = mysql_init( 0 );
> // do something causes an error.
> mysql_close( conn );
> printf( "error: %s", mysql_error( conn ) ); // Messed up.

Boost Exception can be used to transport anything in an exception
object. You can transport error codes as well as error messages:

#include <boost/exception.hpp>

typedef boost::error_info<struct tag_mysql_error_code,int> mysql_error_code;
typedef boost::error_info<struct tag_mysql_error_string,std::string>
mysql_error_string;
struct mysql_err: std::exception, boost::exception { };

....
if( int error=mysql_query(conn,....) )
  throw mysql_err()
    << mysql_error_code(error)
    << mysql_error_string(mysql_error(conn));

Alternatively, if you use shared_ptr to manage the lifetime of the
MYSQL connection, as in:

boost::shared_ptr<MYSQL> conn( mysql_init(0), mysql_close );

you can use an exception object to keep the connection afloat:

typedef boost::error_info<struct tag_mysql_error_code,int> mysql_error_code;
typedef boost::error_info<struct
tag_mysql_error_string,boost::shared_ptr<MYSQL> > mysql_conn;
struct mysql_err: std::exception, boost::exception { };

....
if( int error=mysql_query(conn,....) )
  throw mysql_err()
    << mysql_error_code(error)
    << mysql_conn(conn);

Now, when you catch mysql_err, you can talk to mysql to get the error message:

catch( mysql_err & x )
{
  boost::shared_ptr<MYSQL> conn=*boost::get_error_info<mysql_conn>(x);
  char const * msg=mysql_error(conn.get());
  ....
}

Emil Dotchevski
Reverge Studios, Inc.
http://www.revergestudios.com/reblog/index.php?n=ReCode


Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net