24.3. La API C de MySQL

MySQL 5.0

24.3. La API C de MySQL

The C API code is distributed with MySQL. It is included in the library and allows C programs to access a database.

Many of the clients in the MySQL source distribution are written in C. If you are looking for examples that demonstrate how to use the C API, take a look at these clients. You can find these in the directory in the MySQL source distribution.

Most of the other client APIs (all except Connector/J) use the library to communicate with the MySQL server. This means that, for example, you can take advantage of many of the same environment variables that are used by other client programs, because they are referenced from the library. See Capítulo 8, Programas cliente y utilidades MySQL, for a list of these variables.

The client has a maximum communication buffer size. The size of the buffer that is allocated initially (16KB) is automatically increased up to the maximum size (the maximum is 16MB). Because buffer sizes are increased only as demand warrants, simply increasing the default maximum limit does not in itself cause more resources to be used. This size check is mostly a check for erroneous queries and communication packets.

The communication buffer must be large enough to contain a single SQL statement (for client-to-server traffic) and one row of returned data (for server-to-client traffic). Each thread's communication buffer is dynamically enlarged to handle any query or row up to the maximum limit. For example, if you have values that contain up to 16MB of data, you must have a communication buffer limit of at least 16MB (in both server and client). The client's default maximum is 16MB, but the default maximum in the server is 1MB. You can increase this by changing the value of the parameter when the server is started. See Sección 7.5.2, “Afinar parámetros del servidor”.

The MySQL server shrinks each communication buffer to bytes after each query. For clients, the size of the buffer associated with a connection is not decreased until the connection is closed, at which time client memory is reclaimed.

For programming with threads, see Sección 24.3.15, “Cómo hacer un cliente multihilo”. For creating a standalone application which includes the "server" and "client" in the same program (and does not communicate with an external MySQL server), see Sección 24.3.16, “libmysqld, la biblioteca del servidor MySQL incrustado (embedded)”.

24.3.1. Tipos de datos de la API C

  • This structure represents a handle to one database connection. It is used for almost all MySQL functions. You should not try to make a copy of a structure. There is no guarantee that such a copy will be usable.

  • This structure represents the result of a query that returns rows (, , , ). The information returned from a query is called the result set in the remainder of this section.

  • This is a type-safe representation of one row of data. It is currently implemented as an array of counted byte strings. (You cannot treat these as null-terminated strings if field values may contain binary data, because such values may contain null bytes internally.) Rows are obtained by calling .

  • This structure contains information about a field, such as the field's name, type, and size. Its members are described in more detail here. You may obtain the structures for each field by calling repeatedly. Field values are not part of this structure; they are contained in a structure.

  • This is a type-safe representation of an offset into a MySQL field list. (Used by .) Offsets are field numbers within a row, beginning at zero.

  • The type used for the number of rows and for , , and . This type provides a range of to .

    On some systems, attempting to print a value of type does not work. To print such a value, convert it to and use a print format. Example:

    printf ("Number of rows: %lu\n", (unsigned long) mysql_num_rows(result));
    

The structure contains the members listed here:

  • The name of the field, as a null-terminated string.

  • The name of the table containing this field, if it isn't a calculated field. For calculated fields, the value is an empty string.

  • The default value of this field, as a null-terminated string. This is set only if you use .

  • The type of the field. The value may be one of the symbols shown in the following table.

    Type Value Type Description
    field
    field
    field
    field
    field
    or field
    Precision math or field (MySQL 5.0.3 and up)
    field
    or field
    field
    field
    field
    field
    field
    field
    field
    or field (use to determine the maximum length)
    field
    field
    -type field
    Deprecated; use instead

    You can use the macro to test whether a field has a numeric type. Pass the value to and it evaluates to TRUE if the field is numeric:

    if (IS_NUM(field->type))
        printf("Field is numeric\n");
    

  • The width of the field, as specified in the table definition.

  • The maximum width of the field for the result set (the length of the longest field value for the rows actually in the result set). If you use or , this contains the maximum length for the field. If you use , the value of this variable is zero.

  • Different bit-flags for the field. The value may have zero or more of the following bits set:

    Flag Value Flag Description
    Field can't be
    Field is part of a primary key
    Field is part of a unique key
    Field is part of a non-unique key
    Field has the attribute
    Field has the attribute
    Field has the attribute
    Field has the attribute
    Field is an (deprecated)
    Field is a (deprecated)
    Field is a or (deprecated)
    Field is a (deprecated)

    Use of the , , , and flags is deprecated because they indicate the type of a field rather than an attribute of its type. It is preferable to test against , , , or instead.

    The following example illustrates a typical use of the value:

    if (field->flags & NOT_NULL_FLAG)
        printf("Field can't be null\n");
    

    You may use the following convenience macros to determine the boolean status of the value:

    Flag Status Description
    True if this field is defined as
    True if this field is a primary key
    True if this field is a or (deprecated; test instead)
  • The number of decimals for numeric fields.

24.3.2. Panorámica de funciones de la API C

The functions available in the C API are summarized here and described in greater detail in a later section. See Sección 24.3.3, “Descripción de funciones de la API C”.

Function Description
mysql_affected_rows() Returns the number of rows changed/deleted/inserted by the last , , or query.
mysql_change_user() Changes user and database on an open connection.
mysql_charset_name() Returns the name of the default character set for the connection.
mysql_close() Closes a server connection.
mysql_connect() Connects to a MySQL server. This function is deprecated; use instead.
mysql_create_db() Creates a database. This function is deprecated; use the SQL statement instead.
mysql_data_seek() Seeks to an arbitrary row number in a query result set.
mysql_debug() Does a with the given string.
mysql_drop_db() Drops a database. This function is deprecated; use the SQL statement instead.
mysql_dump_debug_info() Makes the server write debug information to the log.
mysql_eof() Determines whether the last row of a result set has been read. This function is deprecated; or may be used instead.
mysql_errno() Returns the error number for the most recently invoked MySQL function.
mysql_error() Returns the error message for the most recently invoked MySQL function.
mysql_escape_string() Escapes special characters in a string for use in an SQL statement.
mysql_fetch_field() Returns the type of the next table field.
mysql_fetch_field_direct() Returns the type of a table field, given a field number.
mysql_fetch_fields() Returns an array of all field structures.
mysql_fetch_lengths() Returns the lengths of all columns in the current row.
mysql_fetch_row() Fetches the next row from the result set.
mysql_field_seek() Puts the column cursor on a specified column.
mysql_field_count() Returns the number of result columns for the most recent statement.
mysql_field_tell() Returns the position of the field cursor used for the last .
mysql_free_result() Frees memory used by a result set.
mysql_get_client_info() Returns client version information as a string.
mysql_get_client_version() Returns client version information as an integer.
mysql_get_host_info() Returns a string describing the connection.
mysql_get_server_version() Returns version number of server as an integer (new in 4.1).
mysql_get_proto_info() Returns the protocol version used by the connection.
mysql_get_server_info() Returns the server version number.
mysql_info() Returns information about the most recently executed query.
mysql_init() Gets or initializes a structure.
mysql_insert_id() Returns the ID generated for an column by the previous query.
mysql_kill() Kills a given thread.
mysql_library_end() Finalize MySQL C API library.
mysql_library_init() Initialize MySQL C API library.
mysql_list_dbs() Returns database names matching a simple regular expression.
mysql_list_fields() Returns field names matching a simple regular expression.
mysql_list_processes() Returns a list of the current server threads.
mysql_list_tables() Returns table names matching a simple regular expression.
mysql_num_fields() Returns the number of columns in a result set.
mysql_num_rows() Returns the number of rows in a result set.
mysql_options() Sets connect options for .
mysql_ping() Checks whether the connection to the server is working, reconnecting as necessary.
mysql_query() Executes an SQL query specified as a null-terminated string.
mysql_real_connect() Connects to a MySQL server.
mysql_real_escape_string() Escapes special characters in a string for use in an SQL statement, taking into account the current charset of the connection.
mysql_real_query() Executes an SQL query specified as a counted string.
mysql_reload() Tells the server to reload the grant tables.
mysql_row_seek() Seeks to a row offset in a result set, using value returned from .
mysql_row_tell() Returns the row cursor position.
mysql_select_db() Selects a database.
mysql_server_end() Finalize embedded server library.
mysql_server_init() Initialize embedded server library.
mysql_set_server_option() Sets an option for the connection (like ).
mysql_sqlstate() Returns the SQLSTATE error code for the last error.
mysql_shutdown() Shuts down the database server.
mysql_stat() Returns the server status as a string.
mysql_store_result() Retrieves a complete result set to the client.
mysql_thread_id() Returns the current thread ID.
mysql_thread_safe() Returns 1 if the clients are compiled as thread-safe.
mysql_use_result() Initiates a row-by-row result set retrieval.
mysql_warning_count() Returns the warning count for the previous SQL statement.
mysql_commit() Commits the transaction.
mysql_rollback() Rolls back the transaction.
mysql_autocommit() Toggles autocommit mode on/off.
mysql_more_results() Checks whether any more results exist.
mysql_next_result() Returns/initiates the next result in multiple-statement executions.

Application programs should use this general outline for interacting with MySQL:

  1. Initialize the MySQL library by calling . The library can be either the C client library or the embedded server library, depending on whether the application was linked with the or flag.

  2. Initialize a connection handler by calling and connect to the server by calling .

  3. Issue SQL statements and process their results. (The following discussion provides more information about how to do this.)

  4. Close the connection to the MySQL server by calling .

  5. End use of the MySQL library by calling .

The purpose of calling and is to provide proper initialization and finalization of the MySQL library. For applications that are linked with the client library, they provide improved memory management. If you don't call , a block of memory remains allocated. (This does not increase the amount of memory used by the application, but some memory leak detectors will complain about it.) For applications that are linked with the embedded server, these calls start and stop the server.

and are available as of MySQL 4.1.10 and 5.0.3. These actually are symbols that make them equivalent to and , but the names more clearly indicate that they should be called when beginning and ending use of a MySQL library no matter whether the application uses the or library. For older versions of MySQL, you can call and instead.

If you like, the call to may be omitted, because will invoke it automatically as necessary.

To connect to the server, call to initialize a connection handler, then call with that handler (along with other information such as the hostname, username, and password). Upon connection, sets the flag (part of the structure) to a value of in versions of the API strictly older than 5.0.3, of in newer versions. A value of for this flag indicates, in the event that a query cannot be performed because of a lost connection, to try reconnecting to the server before giving up. When you are done with the connection, call to terminate it.

While a connection is active, the client may send SQL queries to the server using or . The difference between the two is that expects the query to be specified as a null-terminated string whereas expects a counted string. If the string contains binary data (which may include null bytes), you must use .

For each non- query (for example, , , ), you can find out how many rows were changed (affected) by calling .

For queries, you retrieve the selected rows as a result set. (Note that some statements are -like in that they return rows. These include , , and . They should be treated the same way as statements.)

There are two ways for a client to process result sets. One way is to retrieve the entire result set all at once by calling . This function acquires from the server all the rows returned by the query and stores them in the client. The second way is for the client to initiate a row-by-row result set retrieval by calling . This function initializes the retrieval, but does not actually get any rows from the server.

In both cases, you access rows by calling . With , accesses rows that have previously been fetched from the server. With , actually retrieves the row from the server. Information about the size of the data in each row is available by calling .

After you are done with a result set, call to free the memory used for it.

The two retrieval mechanisms are complementary. Client programs should choose the approach that is most appropriate for their requirements. In practice, clients tend to use more commonly.

An advantage of is that because the rows have all been fetched to the client, you not only can access rows sequentially, you can move back and forth in the result set using or to change the current row position within the result set. You can also find out how many rows there are by calling . On the other hand, the memory requirements for may be very high for large result sets and you are more likely to encounter out-of-memory conditions.

An advantage of is that the client requires less memory for the result set because it maintains only one row at a time (and because there is less allocation overhead, can be faster). Disadvantages are that you must process each row quickly to avoid tying up the server, you don't have random access to rows within the result set (you can only access rows sequentially), and you don't know how many rows are in the result set until you have retrieved them all. Furthermore, you must retrieve all the rows even if you determine in mid-retrieval that you've found the information you were looking for.

The API makes it possible for clients to respond appropriately to queries (retrieving rows only as necessary) without knowing whether or not the query is a . You can do this by calling after each (or ). If the result set call succeeds, the query was a and you can read the rows. If the result set call fails, call to determine whether a result was actually to be expected. If returns zero, the query returned no data (indicating that it was an , , , etc.), and was not expected to return rows. If is non-zero, the query should have returned rows, but didn't. This indicates that the query was a that failed. See the description for for an example of how this can be done.

Both and allow you to obtain information about the fields that make up the result set (the number of fields, their names and types, etc.). You can access field information sequentially within the row by calling repeatedly, or by field number within the row by calling . The current field cursor position may be changed by calling . Setting the field cursor affects subsequent calls to . You can also get information for fields all at once by calling .

For detecting and reporting errors, MySQL provides access to error information by means of the and functions. These return the error code or error message for the most recently invoked function that can succeed or fail, allowing you to determine when an error occurred and what it was.

24.3.3. Descripción de funciones de la API C

In the descriptions here, a parameter or return value of means in the sense of the C programming language, not a MySQL value.

Functions that return a value generally return a pointer or an integer. Unless specified otherwise, functions returning a pointer return a non- value to indicate success or a value to indicate an error, and functions returning an integer return zero to indicate success or non-zero to indicate an error. Note that “non-zero” means just that. Unless the function description says otherwise, do not test against a value other than zero:

if (result)                   /* correct */
    ... error ...

if (result < 0)               /* incorrect */
    ... error ...

if (result == -1)             /* incorrect */
    ... error ...

When a function returns an error, the Errors subsection of the function description lists the possible types of errors. You can find out which of these occurred by calling . A string representation of the error may be obtained by calling .

24.3.3.1.

Description

Returns the number of rows changed by the last , deleted by the last or inserted by the last statement. May be called immediately after for , , or statements. For statements, works like .

Return Values

An integer greater than zero indicates the number of rows affected or retrieved. Zero indicates that no records were updated for an statement, no rows matched the clause in the query or that no query has yet been executed. -1 indicates that the query returned an error or that, for a query, was called prior to calling . Because returns an unsigned value, you can check for -1 by comparing the return value to (or to , which is equivalent).

Errors

None.

Example

mysql_query(&mysql,"UPDATE products SET cost=cost*1.25 WHERE group=10");
printf("%ld products updated",(long) mysql_affected_rows(&mysql));

If you specify the flag when connecting to mysqld, returns the number of rows matched by the statement for statements.

Note that when you use a command, returns 2 if the new row replaced an old row. This is because in this case one row was inserted after the duplicate was deleted.

If you use to insert a row, returns 1 if the row is inserted as a new row and 2 if an existing row is updated.

24.3.3.2.

Description

Changes the user and causes the database specified by to become the default (current) database on the connection specified by . In subsequent queries, this database is the default for table references that do not include an explicit database specifier.

This function was introduced in MySQL 3.23.3.

fails if the connected user cannot be authenticated or doesn't have permission to use the database. In this case the user and database are not changed

The parameter may be set to if you don't want to have a default database.

Starting from MySQL 4.0.6 this command always performs a of any active transactions, closes all temporary tables, unlocks all locked tables and resets the state as if one had done a new connect. This happens even if the user didn't change.

Return Values

Zero for success. Non-zero if an error occurred.

Errors

The same that you can get from .

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

  • The MySQL server doesn't implement this command (probably an old server).

  • The user or password was wrong.

  • The database didn't exist.

  • The user did not have access rights to the database.

  • The database name was too long.

Example

if (mysql_change_user(&mysql, "user", "password", "new_database"))
{
   fprintf(stderr, "Failed to change user.  Error: %s\n",
           mysql_error(&mysql));
}

24.3.3.3.

Description

Returns the default character set for the current connection.

Return Values

The default character set

Errors

None.

24.3.3.4.

Description

Closes a previously opened connection. also deallocates the connection handle pointed to by if the handle was allocated automatically by or .

Return Values

None.

Errors

None.

24.3.3.5.

Description

This function is deprecated. It is preferable to use instead.

attempts to establish a connection to a MySQL database engine running on . must complete successfully before you can execute any of the other API functions, with the exception of .

The meanings of the parameters are the same as for the corresponding parameters for with the difference that the connection parameter may be . In this case the C API allocates memory for the connection structure automatically and frees it when you call . The disadvantage of this approach is that you can't retrieve an error message if the connection fails. (To get error information from or , you must provide a valid pointer.)

Return Values

Same as for .

Errors

Same as for .

24.3.3.6.

Description

Creates the database named by the parameter.

This function is deprecated. It is preferable to use to issue an SQL statement instead.

Return Values

Zero if the database was created successfully. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

Example

if(mysql_create_db(&mysql, "my_database"))
{
   fprintf(stderr, "Failed to create new database.  Error: %s\n",
           mysql_error(&mysql));
}

24.3.3.7.

Description

Seeks to an arbitrary row in a query result set. The value is a row number and should be in the range from to .

This function requires that the result set structure contains the entire result of the query, so may be used only in conjunction with , not with .

Return Values

None.

Errors

None.

24.3.3.8.

Description

Does a with the given string. uses the Fred Fish debug library. To use this function, you must compile the client library to support debugging. See Sección D.1, “Depurar un servidor MySQL”. See Sección D.2, “Depuración de un cliente MySQL”.

Return Values

None.

Errors

None.

Example

The call shown here causes the client library to generate a trace file in on the client machine:

mysql_debug("d:t:O,/tmp/client.trace");

24.3.3.9.

Description

Drops the database named by the parameter.

This function is deprecated. It is preferable to use to issue an SQL statement instead.

Return Values

Zero if the database was dropped successfully. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

Example

if(mysql_drop_db(&mysql, "my_database"))
  fprintf(stderr, "Failed to drop the database: Error: %s\n",
          mysql_error(&mysql));

24.3.3.10.

Description

Instructs the server to write some debug information to the log. For this to work, the connected user must have the privilege.

Return Values

Zero if the command was successful. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.11.

Description

This function is deprecated. or may be used instead.

determines whether the last row of a result set has been read.

If you acquire a result set from a successful call to , the client receives the entire set in one operation. In this case, a return from always means the end of the result set has been reached and it is unnecessary to call . When used with , always returns true.

On the other hand, if you use to initiate a result set retrieval, the rows of the set are obtained from the server one by one as you call repeatedly. Because an error may occur on the connection during this process, a return value from does not necessarily mean the end of the result set was reached normally. In this case, you can use to determine what happened. returns a non-zero value if the end of the result set was reached and zero if an error occurred.

Historically, predates the standard MySQL error functions and . Because those error functions provide the same information, their use is preferred over , which is deprecated. (In fact, they provide more information, because returns only a boolean value whereas the error functions indicate a reason for the error when one occurs.)

Return Values

Zero if no error occurred. Non-zero if the end of the result set has been reached.

Errors

None.

Example

The following example shows how you might use :

mysql_query(&mysql,"SELECT * FROM some_table");
result = mysql_use_result(&mysql);
while((row = mysql_fetch_row(result)))
{
    // do something with data
}
if(!mysql_eof(result))  // mysql_fetch_row() failed due to an error
{
    fprintf(stderr, "Error: %s\n", mysql_error(&mysql));
}

However, you can achieve the same effect with the standard MySQL error functions:

mysql_query(&mysql,"SELECT * FROM some_table");
result = mysql_use_result(&mysql);
while((row = mysql_fetch_row(result)))
{
    // do something with data
}
if(mysql_errno(&mysql))  // mysql_fetch_row() failed due to an error
{
    fprintf(stderr, "Error: %s\n", mysql_error(&mysql));
}

24.3.3.12.

Description

For the connection specified by , returns the error code for the most recently invoked API function that can succeed or fail. A return value of zero means that no error occurred. Client error message numbers are listed in the MySQL header file. Server error message numbers are listed in . In the MySQL source distribution you can find a complete list of error messages and error numbers in the file . The server error codes also are listed at Capítulo 26, Manejo de errores en MySQL.

Note that some functions like don't set if they succeed.

A rule of thumb is that all functions that have to ask the server for information reset if they succeed.

Return Values

An error code value for the last () call, if it failed. zero means no error occurred.

Errors

None.

24.3.3.13.

Description

For the connection specified by , returns a null-terminated string containing the error message for the most recently invoked API function that failed. If a function didn't fail, the return value of may be the previous error or an empty string to indicate no error.

A rule of thumb is that all functions that have to ask the server for information reset if they succeed.

For functions that reset , the following two tests are equivalent:

if(mysql_errno(&mysql))
{
    // an error occurred
}

if(mysql_error(&mysql)[0] != '\0')
{
    // an error occurred
}

The language of the client error messages may be changed by recompiling the MySQL client library. Currently you can choose error messages in several different languages. See Sección 5.9.2, “Escoger el idioma de los mensajes de error”.

Return Values

A null-terminated character string that describes the error. An empty string if no error occurred.

Errors

None.

24.3.3.14.

You should use instead!

This function is identical to except that takes a connection handler as its first argument and escapes the string according to the current character set. does not take a connection argument and does not respect the current charset setting.

24.3.3.15.

Description

Returns the definition of one column of a result set as a structure. Call this function repeatedly to retrieve information about all columns in the result set. returns when no more fields are left.

is reset to return information about the first field each time you execute a new query. The field returned by is also affected by calls to .

If you've called to perform a on a table but have not called , MySQL returns the default blob length (8KB) if you call to ask for the length of a field. (The 8KB size is chosen because MySQL doesn't know the maximum length for the . This should be made configurable sometime.) Once you've retrieved the result set, contains the length of the largest value for this column in the specific query.

Return Values

The structure for the current column. if no columns are left.

Errors

None.

Example

MYSQL_FIELD *field;

while((field = mysql_fetch_field(result)))
{
    printf("field name %s\n", field->name);
}

24.3.3.16.

Description

Returns an array of all structures for a result set. Each structure provides the field definition for one column of the result set.

Return Values

An array of structures for all columns of a result set.

Errors

None.

Example

unsigned int num_fields;
unsigned int i;
MYSQL_FIELD *fields;

num_fields = mysql_num_fields(result);
fields = mysql_fetch_fields(result);
for(i = 0; i < num_fields; i++)
{
   printf("Field %u is %s\n", i, fields[i].name);
}

24.3.3.17.

Description

Given a field number for a column within a result set, returns that column's field definition as a structure. You may use this function to retrieve the definition for an arbitrary column. The value of should be in the range from 0 to .

Return Values

The structure for the specified column.

Errors

None.

Example

unsigned int num_fields;
unsigned int i;
MYSQL_FIELD *field;

num_fields = mysql_num_fields(result);
for(i = 0; i < num_fields; i++)
{
    field = mysql_fetch_field_direct(result, i);
    printf("Field %u is %s\n", i, field->name);
}

24.3.3.18.

Description

Returns the lengths of the columns of the current row within a result set. If you plan to copy field values, this length information is also useful for optimization, because you can avoid calling . In addition, if the result set contains binary data, you must use this function to determine the size of the data, because returns incorrect results for any field containing null characters.

The length for empty columns and for columns containing values is zero. To see how to distinguish these two cases, see the description for .

Return Values

An array of unsigned long integers representing the size of each column (not including any terminating null characters). if an error occurred.

Errors

is valid only for the current row of the result set. It returns if you call it before calling or after retrieving all rows in the result.

Example

MYSQL_ROW row;
unsigned long *lengths;
unsigned int num_fields;
unsigned int i;

row = mysql_fetch_row(result);
if (row)
{
    num_fields = mysql_num_fields(result);
    lengths = mysql_fetch_lengths(result);
    for(i = 0; i < num_fields; i++)
    {
         printf("Column %u is %lu bytes in length.\n", i, lengths[i]);
    }
}

24.3.3.19.

Description

Retrieves the next row of a result set. When used after , returns when there are no more rows to retrieve. When used after , returns when there are no more rows to retrieve or if an error occurred.

The number of values in the row is given by . If holds the return value from a call to , pointers to the values are accessed as to . values in the row are indicated by pointers.

The lengths of the field values in the row may be obtained by calling . Empty fields and fields containing both have length 0; you can distinguish these by checking the pointer for the field value. If the pointer is , the field is ; otherwise, the field is empty.

Return Values

A structure for the next row. if there are no more rows to retrieve or if an error occurred.

Errors

Note that error is not reset between calls to

  • The connection to the server was lost during the query.

  • An unknown error occurred.

Example

MYSQL_ROW row;
unsigned int num_fields;
unsigned int i;

num_fields = mysql_num_fields(result);
while ((row = mysql_fetch_row(result)))
{
   unsigned long *lengths;
   lengths = mysql_fetch_lengths(result);
   for(i = 0; i < num_fields; i++)
   {
       printf("[%.*s] ", (int) lengths[i], row[i] ? row[i] : "NULL");
   }
   printf("\n");
}

24.3.3.20.

If you are using a version of MySQL earlier than Version 3.22.24, you should use instead.

Description

Returns the number of columns for the most recent query on the connection.

The normal use of this function is when returned (and thus you have no result set pointer). In this case, you can call to determine whether should have produced a non-empty result. This allows the client program to take proper action without knowing whether the query was a (or -like) statement. The example shown here illustrates how this may be done.

See Sección 24.3.13.1, “¿Por qué a veces devuelve después de que haya dado un resultado?”.

Return Values

An unsigned integer representing the number of columns in a result set.

Errors

None.

Example

MYSQL_RES *result;
unsigned int num_fields;
unsigned int num_rows;

if (mysql_query(&mysql,query_string))
{
    // error
}
else // query succeeded, process any data returned by it
{
    result = mysql_store_result(&mysql);
    if (result)  // there are rows
    {
        num_fields = mysql_num_fields(result);
        // retrieve rows, then call mysql_free_result(result)
    }
    else  // mysql_store_result() returned nothing; should it have?
    {
        if(mysql_field_count(&mysql) == 0)
        {
            // query does not return data
            // (it was not a SELECT)
            num_rows = mysql_affected_rows(&mysql);
        }
        else // mysql_store_result() should have returned data
        {
            fprintf(stderr, "Error: %s\n", mysql_error(&mysql));
        }
    }
}

An alternative is to replace the call with . In this case, you are checking directly for an error from rather than inferring from the value of whether the statement was a .

24.3.3.21.

Description

Sets the field cursor to the given offset. The next call to retrieves the field definition of the column associated with that offset.

To seek to the beginning of a row, pass an value of zero.

Return Values

The previous value of the field cursor.

Errors

None.

24.3.3.22.

Description

Returns the position of the field cursor used for the last . This value can be used as an argument to .

Return Values

The current offset of the field cursor.

Errors

None.

24.3.3.23.

Description

Frees the memory allocated for a result set by , , , etc. When you are done with a result set, you must free the memory it uses by calling .

Do not attempt to access a result set after freeing it.

Return Values

None.

Errors

None.

24.3.3.24.

Description

This function provides information about the default client character set. The default character set may be changed with the function.

This function was added in MySQL 5.0.10.

Example

if (!mysql_set_character_set_name(&mysql, "utf8"))
{
    MY_CHARSET_INFO cs;
    mysql_get_character_set_info(&mysql, &cs);
    printf("character set information:\n");
    printf("character set name: %s\n", cs->name);
    printf("collation name: %s\n", cs->csname);
    printf("comment: %s\n", cs->comment);
    printf("directory: %s\n", cs->dir);
    printf("multi byte character min. length: %s\n", cs->mbminlen);
    printf("multi byte character max. length: %s\n", cs->mbmaxlen);
}

24.3.3.25.

Description

Returns a string that represents the client library version.

Return Values

A character string that represents the MySQL client library version.

Errors

None.

24.3.3.26.

Description

Returns an integer that represents the client library version. The value has the format where is the major version, is the release level, and is the version number within the release level. For example, a value of represents a client library version of .

This function was added in MySQL 4.0.16.

Return Values

An integer that represents the MySQL client library version.

Errors

None.

24.3.3.27.

Description

Returns a string describing the type of connection in use, including the server hostname.

Return Values

A character string representing the server hostname and the connection type.

Errors

None.

24.3.3.28.

Description

Returns the protocol version used by current connection.

Return Values

An unsigned integer representing the protocol version used by the current connection.

Errors

None.

24.3.3.29.

Description

Returns a string that represents the server version number.

Return Values

A character string that represents the server version number.

Errors

None.

24.3.3.30.

Description

Returns the version number of the server as an integer.

This function was added in MySQL 4.1.0.

Return Values

A number that represents the MySQL server version in this format:

major_version*10000 + minor_version *100 + sub_version

For example, 4.1.2 is returned as 40102.

This function is useful in client programs for quickly determining whether some version-specific server capability exists.

Errors

None.

24.3.3.31.

Description

This function is used to create a legal SQL string that you can use in a SQL statement. See Sección 9.1.1, “Cadenas de caracteres”.

The string in is encoded to hexadecimal format, with each character encoded as two hexadecimal digits. The result is placed in and a terminating null byte is appended.

The string pointed to by must be bytes long. You must allocate the buffer to be at least bytes long. When returns, the contents of is a null-terminated string. The return value is the length of the encoded string, not including the terminating null character.

The return value can be placed into an SQL statement using either or ' format. However, the return value does not include the or . The caller must supply whichever of those is desired.

was added in MySQL 4.0.23 and 4.1.8.

Example

char query[1000],*end;

end = strmov(query,"INSERT INTO test_table values(");
end = strmov(end,"0x");
end += mysql_hex_string(end,"What's this",11);
end = strmov(end,",0x");
end += mysql_hex_string(end,"binary data: \0\r\n",16);
*end++ = ')';

if (mysql_real_query(&mysql,query,(unsigned int) (end - query)))
{
   fprintf(stderr, "Failed to insert row, Error: %s\n",
           mysql_error(&mysql));
}

The function used in the example is included in the library and works like but returns a pointer to the terminating null of the first parameter.

Return Values

The length of the value placed into , not including the terminating null character.

Errors

None.

24.3.3.32.

Description

Retrieves a string providing information about the most recently executed query, but only for the statements listed here. For other statements, returns . The format of the string varies depending on the type of query, as described here. The numbers are illustrative only; the string contains values appropriate for the query.

  • String format:

  • String format:

  • String format:

  • String format:

  • String format:

Note that returns a non- value for only for the multiple-row form of the statement (that is, only if multiple value lists are specified).

Return Values

A character string representing additional information about the most recently executed query. if no information is available for the query.

Errors

None.

24.3.3.33.

Description

Allocates or initializes a object suitable for . If is a pointer, the function allocates, initializes, and returns a new object. Otherwise, the object is initialized and the address of the object is returned. If allocates a new object, it is freed when is called to close the connection.

Return Values

An initialized handle. if there was insufficient memory to allocate a new object.

Errors

In case of insufficient memory, is returned.

24.3.3.34.

Description

Returns the value generated for an column by the previous or statement. Use this function after you have performed an statement into a table that contains an field.

More precisely, is updated under these conditions:

  • statements that store a value into an column. This is true whether the value is automatically generated by storing the special values or into the column, or is an explicit non-special value.

  • In the case of a multiple-row statement, returns the first automatically generated value; if no such value is generated, it returns the last last explicit value inserted into the column.

  • statements that generate an value by inserting ) into any column.

  • statements that generate an value by updating any column to ).

  • The value of is not affected by statements such as that return a result set.

  • If the previous statement returned an error, the value of is undefined.

Note that returns if the previous statement does not use an value. If you need to save the value for later, be sure to call immediately after the statement that generates the value.

The value of is affected only by statements issued within the current client connection. It is not affected by statements issued by other clients.

See Sección 12.9.3, “Funciones de información”.

Also note that the value of the SQL function always contains the most recently generated value, and is not reset between statements because the value of that function is maintained in the server. Another difference is that is not updated if you set an column to a specific non-special value.

The reason for the difference between and is that is made easy to use in scripts while tries to provide a little more exact information of what happens to the column.

Return Values

Described in the preceding discussion.

Errors

None.

24.3.3.35.

Description

Asks the server to kill the thread specified by .

Return Values

Zero for success. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.36.

Description

This is a synonym for the function. It was added in MySQL 4.1.10 and 5.0.3.

See Sección 24.3.2, “Panorámica de funciones de la API C” for usage information.

24.3.3.37.

Description

This is a synonym for the function. It was added in MySQL 4.1.10 and 5.0.3.

See Sección 24.3.2, “Panorámica de funciones de la API C” for usage information.

24.3.3.38.

Description

Returns a result set consisting of database names on the server that match the simple regular expression specified by the parameter. may contain the wildcard characters '' or '', or may be a pointer to match all databases. Calling is similar to executing the query .

You must free the result set with .

Return Values

A result set for success. if an error occurred.

Errors

  • Commands were executed in an improper order.

  • Out of memory.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.39.

Description

Returns a result set consisting of field names in the given table that match the simple regular expression specified by the parameter. may contain the wildcard characters '' or '', or may be a pointer to match all fields. Calling is similar to executing the query [LIKE ].

Note that it's recommended that you use instead of .

You must free the result set with .

Return Values

A result set for success. if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.40.

Description

Returns a result set describing the current server threads. This is the same kind of information as that reported by mysqladmin processlist or a query.

You must free the result set with .

Return Values

A result set for success. if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.41.

Description

Returns a result set consisting of table names in the current database that match the simple regular expression specified by the parameter. may contain the wildcard characters '' or '', or may be a pointer to match all tables. Calling is similar to executing the query .

You must free the result set with .

Return Values

A result set for success. if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.42.

Or:

The second form doesn't work on MySQL 3.22.24 or newer. To pass a argument, you must use instead.

Description

Returns the number of columns in a result set.

Note that you can get the number of columns either from a pointer to a result set or to a connection handle. You would use the connection handle if or returned (and thus you have no result set pointer). In this case, you can call to determine whether should have produced a non-empty result. This allows the client program to take proper action without knowing whether or not the query was a (or -like) statement. The example shown here illustrates how this may be done.

See Sección 24.3.13.1, “¿Por qué a veces devuelve después de que haya dado un resultado?”.

Return Values

An unsigned integer representing the number of columns in a result set.

Errors

None.

Example

MYSQL_RES *result;
unsigned int num_fields;
unsigned int num_rows;

if (mysql_query(&mysql,query_string))
{
    // error
}
else // query succeeded, process any data returned by it
{
    result = mysql_store_result(&mysql);
    if (result)  // there are rows
    {
        num_fields = mysql_num_fields(result);
        // retrieve rows, then call mysql_free_result(result)
    }
    else  // mysql_store_result() returned nothing; should it have?
    {
        if (mysql_errno(&mysql))
        {
           fprintf(stderr, "Error: %s\n", mysql_error(&mysql));
        }
        else if (mysql_field_count(&mysql) == 0)
        {
            // query does not return data
            // (it was not a SELECT)
            num_rows = mysql_affected_rows(&mysql);
        }
    }
}

An alternative (if you know that your query should have returned a result set) is to replace the call with a check whether is = 0. This happens only if something went wrong.

24.3.3.43.

Description

Returns the number of rows in the result set.

The use of depends on whether you use or to return the result set. If you use , may be called immediately. If you use , does not return the correct value until all the rows in the result set have been retrieved.

Return Values

The number of rows in the result set.

Errors

None.

24.3.3.44.

Description

Can be used to set extra connect options and affect behavior for a connection. This function may be called multiple times to set several options.

should be called after and before or .

The argument is the option that you want to set; the argument is the value for the option. If the option is an integer, then should point to the value of the integer.

Possible option values:

Option Argument Type Function
Command to execute when connecting to the MySQL server. Will automatically be re-executed when reconnecting.
Not used Use the compressed client/server protocol.
Connect timeout in seconds.
Not used For an application linked against , this allows the library to guess whether to use the embedded server or a remote server. “Guess” means that if the hostname is set and is not , it uses a remote server. This behavior is the default. and can be used to override it. This option is ignored for applications linked against .
optional pointer to uint If no pointer is given or if pointer points to an the command is enabled.
Not used Use named pipes to connect to a MySQL server on NT.
Type of protocol to use. Should be one of the enum values of defined in . New in 4.1.0.
Timeout for reads from server (works currently only on Windows on TCP/IP connections). New in 4.1.1.
For an application linked against linked against (with compiled with authentication support), this means that the user is considered to have connected from the specified IP address (specified as a string) for authentication purposes. This option is ignored for applications linked against .
Not used For an application linked against , this forces the use of the embedded server for the connection. This option is ignored for applications linked against .
Not used For an application linked against , this forces the use of a remote server for the connection. This option is ignored for applications linked against .
Not used This option is new in 4.1.1, but is unused.
Timeout for writes to server (works currently only on Windows on TCP/IP connections). New in 4.1.1.
Read options from the named option file instead of from .
Read options from the named group from or the file specified with .
Enable or disable reporting of data truncation errors for prepared statements via . (Default: disabled) New in 5.0.3.
Whether to connect to a server that does not support the new 4.1.1 password hashing. New in 4.1.1.
The pathname to the directory that contains character set definition files.
The name of the character set to use as the default character set.
Named of shared memory object for communication to server. Should be same as the option used for the mysqld server you want's to connect to. New in 4.1.0.

Note that the group is always read if you use or .

The specified group in the option file may contain the following options:

Option Description
Connect timeout in seconds. On Linux this timeout is also used for waiting for the first answer from the server.
Use the compressed client/server protocol.
Connect to this database if no database was specified in the connect command.
Debug options.
Disable use of .
Default hostname.
Command to execute when connecting to MySQL server. Will automatically be re-executed when reconnecting.
Same as specifying to . See Sección 24.3.3.47, “.
If no argument or argument != 0 then enable use of .
Max size of packet client can read from server.
Allow multiple result sets from multiple-statement executions or stored procedures. New in 4.1.1.
Allow the client to send multiple statements in a single string (separated by ''). New in 4.1.9.
Default password.
Use named pipes to connect to a MySQL server on NT.
The protocol to use when connecting to server (New in 4.1)
Default port number.
Tell to return found rows instead of updated rows when using .
Shared memory name to use to connect to server (default is "MYSQL"). New in MySQL 4.1.
Default socket file.
Default user.

Note that has been replaced by , but still works for a while.

For more information about option files, see Sección 4.3.2, “Usar ficheros de opciones”.

Return Values

Zero for success. Non-zero if you used an unknown option.

Example

MYSQL mysql;

mysql_init(&mysql);
mysql_options(&mysql,MYSQL_OPT_COMPRESS,0);
mysql_options(&mysql,MYSQL_READ_DEFAULT_GROUP,"odbc");
if (!mysql_real_connect(&mysql,"host","user","passwd","database",0,NULL,0))
{
    fprintf(stderr, "Failed to connect to database: Error: %s\n",
          mysql_error(&mysql));
}

This code requests the client to use the compressed client/server protocol and read the additional options from the section in the file.

24.3.3.45.

Description

Checks whether the connection to the server is working. If the connection has gone down, an automatic reconnection is attempted.

This function can be used by clients that remain idle for a long while, to check whether the server has closed the connection and reconnect if necessary.

Return Values

Zero if the connection to the server is alive. Non-zero if an error occurred. A non-zero return does not indicate whether the MySQL server itself is down; the connection might be broken for other reasons such as network problems.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • An unknown error occurred.

24.3.3.46.

Description

Executes the SQL query pointed to by the null-terminated string . Normally, the string must consist of a single SQL statement and you should not add a terminating semicolon ('') or to the statement. If multiple-statement execution has been enabled, the string can contain several statements separated by semicolons. See Sección 24.3.9, “Tratamiento por parte de la API C de la ejecución de múltiples consultas”.

cannot be used for queries that contain binary data; you should use instead. (Binary data may contain the '' character, which interprets as the end of the query string.)

If you want to know whether the query should return a result set, you can use to check for this. See Sección 24.3.3.20, “.

Return Values

Zero if the query was successful. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.47.

Description

attempts to establish a connection to a MySQL database engine running on . must complete successfully before you can execute any other API functions that require a valid connection handle structure.

The parameters are specified as follows:

  • The first parameter should be the address of an existing structure. Before calling you must call to initialize the structure. You can change a lot of connect options with the call. See Sección 24.3.3.44, “.

  • The value of may be either a hostname or an IP address. If is or the string , a connection to the local host is assumed. If the OS supports sockets (Unix) or named pipes (Windows), they are used instead of TCP/IP to connect to the server.

  • The parameter contains the user's MySQL login ID. If is or the empty string , the current user is assumed. Under Unix, this is the current login name. Under Windows ODBC, the current username must be specified explicitly. See Sección 25.1.9.2, “Configuración de una DSN para MyODBC en Windows”.

  • The parameter contains the password for . If is , only entries in the table for the user that have a blank (empty) password field are checked for a match. This allows the database administrator to set up the MySQL privilege system in such a way that users get different privileges depending on whether or not they have specified a password.

    Note: Do not attempt to encrypt the password before calling ; password encryption is handled automatically by the client API.

  • is the database name. If is not , the connection sets the default database to this value.

  • If is not 0, the value is used as the port number for the TCP/IP connection. Note that the parameter determines the type of the connection.

  • If is not , the string specifies the socket or named pipe that should be used. Note that the parameter determines the type of the connection.

  • The value of is usually 0, but can be set to a combination of the following flags in very special circumstances:

    Flag Name Flag Description
    Use compression protocol.
    Return the number of found (matched) rows, not the number of affected rows.
    Allow spaces after function names. Makes all functions names reserved words.
    Allow seconds (instead of seconds) of inactivity before closing the connection. The client's session variable is set to the value of the session variable.
    Enable handling.
    Tell the server that the client may send multiple statements in a single string (separated by ''). If this flag is not set, multiple-statement execution is disabled. New in 4.1.
    Tell the server that the client can handle multiple result sets from multiple-statement executions or stored procedures. This is automatically set if is set. New in 4.1.
    Don't allow the syntax. This is for ODBC. It causes the parser to generate an error if you use that syntax, which is useful for trapping bugs in some ODBC programs.
    The client is an ODBC client. This changes mysqld to be more ODBC-friendly.
    Use SSL (encrypted protocol). This option should not be set by application programs; it is set internally in the client library.

Return Values

A connection handle if the connection was successful, if the connection was unsuccessful. For a successful connection, the return value is the same as the value of the first parameter.

Errors

  • Failed to connect to the MySQL server.

  • Failed to connect to the local MySQL server.

  • Failed to create an IP socket.

  • Out of memory.

  • Failed to create a Unix socket.

  • Failed to find the IP address for the hostname.

  • A protocol mismatch resulted from attempting to connect to a server with a client library that uses a different protocol version. This can happen if you use a very old client library to connect to a new server that wasn't started with the option.

  • Failed to create a named pipe on Windows.

  • Failed to wait for a named pipe on Windows.

  • Failed to get a pipe handler on Windows.

  • If > 0 and it took longer than seconds to connect to the server or if the server died while executing the .

Example

MYSQL mysql;

mysql_init(&mysql);
mysql_options(&mysql,MYSQL_READ_DEFAULT_GROUP,"your_prog_name");
if (!mysql_real_connect(&mysql,"host","user","passwd","database",0,NULL,0))
{
    fprintf(stderr, "Failed to connect to database: Error: %s\n",
          mysql_error(&mysql));
}

By using the MySQL library reads the and sections in the file which ensures that your program works, even if someone has set up MySQL in some non-standard way.

Note that upon connection, sets the flag (part of the structure) to a value of in versions of the API strictly older than 5.0.3, of in newer versions. A value of for this flag indicates, in the event that a query cannot be performed because of a lost connection, to try reconnecting to the server before giving up.

24.3.3.48.

Note that must be a valid, open connection. This is needed because the escaping depends on the character set in use by the server.

Description

This function is used to create a legal SQL string that you can use in a SQL statement. See Sección 9.1.1, “Cadenas de caracteres”.

The string in is encoded to an escaped SQL string, taking into account the current character set of the connection. The result is placed in and a terminating null byte is appended. Characters encoded are (ASCII 0), '', '', '', '', '', and Control-Z (see Sección 9.1, “Valores literales”). (Strictly speaking, MySQL requires only that backslash and the quote character used to quote the string in the query be escaped. This function quotes the other characters to make them easier to read in log files.)

The string pointed to by must be bytes long. You must allocate the buffer to be at least bytes long. (In the worst case, each character may need to be encoded as using two bytes, and you need room for the terminating null byte.) When returns, the contents of is a null-terminated string. The return value is the length of the encoded string, not including the terminating null character.

If you need to change the character set of the connection, you should use the function rather than executing a (or ) statement. works like but also affects the character set used by , which does not.

Example

char query[1000],*end;

end = strmov(query,"INSERT INTO test_table values(");
*end++ = '\'';
end += mysql_real_escape_string(&mysql, end,"What's this",11);
*end++ = '\'';
*end++ = ',';
*end++ = '\'';
end += mysql_real_escape_string(&mysql, end,"binary data: \0\r\n",16);
*end++ = '\'';
*end++ = ')';

if (mysql_real_query(&mysql,query,(unsigned int) (end - query)))
{
   fprintf(stderr, "Failed to insert row, Error: %s\n",
           mysql_error(&mysql));
}

The function used in the example is included in the library and works like but returns a pointer to the terminating null of the first parameter.

Return Values

The length of the value placed into , not including the terminating null character.

Errors

None.

24.3.3.49.

Description

Executes the SQL query pointed to by , which should be a string bytes long. Normally, the string must consist of a single SQL statement and you should not add a terminating semicolon ('') or to the statement. If multiple-statement execution has been enabled, the string can contain several statements separated by semicolons. See Sección 24.3.9, “Tratamiento por parte de la API C de la ejecución de múltiples consultas”.

You must use rather than for queries that contain binary data, because binary data may contain the '' character. In addition, is faster than because it does not call on the query string.

If you want to know whether the query should return a result set, you can use to check for this. See Sección 24.3.3.20, “.

Return Values

Zero if the query was successful. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.50.

Description

Asks the MySQL server to reload the grant tables. The connected user must have the privilege.

This function is deprecated. It is preferable to use to issue an SQL statement instead.

Return Values

Zero for success. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.51.

Description

Sets the row cursor to an arbitrary row in a query result set. The value is a row offset that should be a value returned from or from . This value is not a row number; if you want to seek to a row within a result set by number, use instead.

This function requires that the result set structure contains the entire result of the query, so may be used only in conjunction with , not with .

Return Values

The previous value of the row cursor. This value may be passed to a subsequent call to .

Errors

None.

24.3.3.52.

Description

Returns the current position of the row cursor for the last . This value can be used as an argument to .

You should use only after , not after .

Return Values

The current offset of the row cursor.

Errors

None.

24.3.3.53.

Description

Causes the database specified by to become the default (current) database on the connection specified by . In subsequent queries, this database is the default for table references that do not include an explicit database specifier.

fails unless the connected user can be authenticated as having permission to use the database.

Return Values

Zero for success. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.54.

Description

This function is used to set the default character set for the current connection. The string specifies a valid character set name. The connection collation becomes the default collation of the character set. This function works like the statement, but also sets the value of , and thus affects the character set used by

This function was added in MySQL 5.0.7.

Return Values

Zero for success. Non-zero if an error occurred.

Example

MYSQL mysql;

mysql_init(&mysql);
if (!mysql_real_connect(&mysql,"host","user","passwd","database",0,NULL,0))
{
    fprintf(stderr, "Failed to connect to database: Error: %s\n",
          mysql_error(&mysql));
}

if (!mysql_set_charset_name(&mysql, "utf8")) 
{
    printf("New client character set: %s\n", mysql_character_set_name(&mysql));
}

24.3.3.55.

Description

Enables or disables an option for the connection. can have one of the following values:

MYSQL_OPTION_MULTI_STATEMENTS_ON Enable multi statement support.
MYSQL_OPTION_MULTI_STATEMENTS_OFF Disable multi statement support.

This function was added in MySQL 4.1.1.

Return Values

Zero for success. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • The server didn't support (which is the case that the server is older than 4.1.1) or the server didn't support the option one tried to set.

24.3.3.56.

Description

Asks the database server to shut down. The connected user must have privileges. The argument was added in MySQL 4.1.3 (and 5.0.1). The MySQL server currently supports only one type (level of gracefulness) of shutdown; must be equal to . Later we wil add more levels and then the argument will enable us to choose the desired level. MySQL servers and MySQL clients before and after 4.1.3 are compatible; MySQL servers newer than 4.1.3 accept the call, and MySQL servers older than 4.1.3 accept the new call. But dynamically linked executables which have been compiled with older versions of headers, and call , need to be used with the old dynamic library.

The shutdown process is described in Sección 5.4, “El proceso de cierre del servidor MySQL”.

Return Values

Zero for success. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.57.

Description

Returns a null-terminated string containing the SQLSTATE error code for the last error. The error code consists of five characters. means “no error.” The values are specified by ANSI SQL and ODBC. For a list of possible values, see Capítulo 26, Manejo de errores en MySQL.

Note that not all MySQL errors are yet mapped to SQLSTATE's. The value (general error) is used for unmapped errors.

This function was added to MySQL 4.1.1.

Return Values

A null-terminated character string containing the SQLSTATE error code.

See Also

See Sección 24.3.3.12, “. See Sección 24.3.3.13, “. See Sección 24.3.7.26, “.

24.3.3.58.

Description

is used for establishing secure connections using SSL. It must be called before .

does nothing unless OpenSSL support is enabled in the client library.

is the connection handler returned from . The other parameters are specified as follows:

  • is the pathname to the key file.

  • is the pathname to the certificate file.

  • is the pathname to the certificate authority file.

  • is the pathname to a directory that contains trusted SSL CA certificates in pem format.

  • is a list of allowable ciphers to use for SSL encryption.

Any unused SSL parameters may be given as .

Return Values

This function always returns . If SSL setup is incorrect, returns an error when you attempt to connect.

24.3.3.59.

Description

Returns a character string containing information similar to that provided by the mysqladmin status command. This includes uptime in seconds and the number of running threads, questions, reloads, and open tables.

Return Values

A character string describing the server status. if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.60.

Description

You must call or for every query that successfully retrieves data (, , , , , and so forth).

You don't have to call or for other queries, but it does not do any harm or cause any notable performance degredation if you call in all cases. You can detect if the query didn't have a result set by checking if returns 0 (more about this later on).

If you want to know whether the query should return a result set, you can use to check for this. See Sección 24.3.3.20, “.

reads the entire result of a query to the client, allocates a structure, and places the result into this structure.

returns a null pointer if the query didn't return a result set (if the query was, for example, an statement).

also returns a null pointer if reading of the result set failed. You can check whether an error occurred by checking if returns a non-empty string, if returns non-zero, or if returns zero.

An empty result set is returned if there are no rows returned. (An empty result set differs from a null pointer as a return value.)

Once you have called and got a result back that isn't a null pointer, you may call to find out how many rows are in the result set.

You can call to fetch rows from the result set, or and to obtain or set the current row position within the result set.

You must call once you are done with the result set.

See Sección 24.3.13.1, “¿Por qué a veces devuelve después de que haya dado un resultado?”.

Return Values

A result structure with the results. if an error occurred.

Errors

resets and if it succeeds.

  • Commands were executed in an improper order.

  • Out of memory.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.61.

Description

Returns the thread ID of the current connection. This value can be used as an argument to to kill the thread.

If the connection is lost and you reconnect with , the thread ID changes. This means you should not get the thread ID and store it for later. You should get it when you need it.

Return Values

The thread ID of the current connection.

Errors

None.

24.3.3.62.

Description

You must call or for every query that successfully retrieves data (, , , ).

initiates a result set retrieval but does not actually read the result set into the client like does. Instead, each row must be retrieved individually by making calls to . This reads the result of a query directly from the server without storing it in a temporary table or local buffer, which is somewhat faster and uses much less memory than . The client allocates memory only for the current row and a communication buffer that may grow up to bytes.

On the other hand, you shouldn't use if you are doing a lot of processing for each row on the client side, or if the output is sent to a screen on which the user may type a (stop scroll). This ties up the server and prevent other threads from updating any tables from which the data is being fetched.

When using , you must execute until a value is returned, otherwise, the unfetched rows are returned as part of the result set for your next query. The C API gives the error if you forget to do this!

You may not use , , , , or with a result returned from , nor may you issue other queries until the has finished. (However, after you have fetched all the rows, accurately returns the number of rows fetched.)

You must call once you are done with the result set.

Return Values

A result structure. if an error occurred.

Errors

resets and if it succeeds.

  • Commands were executed in an improper order.

  • Out of memory.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.3.63.

Description

Returns the number of warnings generated during execution of the previous SQL statement.

This function was added in MySQL 4.1.0.

Return Values

The warning count.

Errors

None.

24.3.3.64.

Description

Commits the current transaction.

This function was added in MySQL 4.1.0.

Return Values

Zero if successful. Non-zero if an error occurred.

Errors

None.

24.3.3.65.

Description

Rolls back the current transaction.

This function was added in MySQL 4.1.0.

Return Values

Zero if successful. Non-zero if an error occurred.

Errors

None.

24.3.3.66.

Description

Sets autocommit mode on if is 1, off if is 0.

This function was added in MySQL 4.1.0.

Return Values

Zero if successful. Non-zero if an error occurred.

Errors

None.

24.3.3.67.

Description

Returns true if more results exist from the currently executed query, and the application must call to fetch the results.

This function was added in MySQL 4.1.0.

Return Values

(1) if more results exist. (0) if no more results exist.

In most cases, you can call instead to test whether more results exist and initiate retrieval if so.

See Sección 24.3.9, “Tratamiento por parte de la API C de la ejecución de múltiples consultas”. See Sección 24.3.3.68, “.

Errors

None.

24.3.3.68.

Description

If more query results exist, reads the next query results and returns the status back to application.

You must call for the preceding query if it returned a result set.

After calling the state of the connection is as if you had called or for the next query. This means that you can call , , , and so forth.

If returns an error, no other statements are executed and there are no more results to fetch.

See Sección 24.3.9, “Tratamiento por parte de la API C de la ejecución de múltiples consultas”.

This function was added in MySQL 4.1.0.

Return Values

Return Value Description
0 Successful and there are more results
-1 Successful and there are no more results
>0 An error occurred

Errors

  • Commands were executed in an improper order. For example if you didn't call for a previous result set.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.4. Sentencias preparadas de la API C

As of MySQL 4.1, the client/server protocol provides for the use of prepared statements. This capability uses the statement handler data structure returned by the initialization function. Prepared execution is an efficient way to execute a statement more than once. The statement is first parsed to prepare it for execution. Then it is executed one or more times at a later time, using the statement handle returned by the initialization function.

Prepared execution is faster than direct execution for statements executed more than once, primarily because the query is parsed only once. In the case of direct execution, the query is parsed every time it is executed. Prepared execution also can provide a reduction of network traffic because for each execution of the prepared statement, it is necessary only to send the data for the parameters.

Another advantage of prepared statements is that it uses a binary protocol that makes data transfer between client and server more efficient.

The following statements can be used as prepared statements: , , , , , , , , and most statements. Other statements are not yet supported.

24.3.5. Tipos de datos de sentencias preparadas de la API C

Note: Some incompatible changes were made in MySQL 4.1.2. See Sección 24.3.7, “Descripciones de funciones de sentencias preparadas de la API C” for details.

Prepared statements mainly use the and data structures. A third structure, , is used to transfer temporal data.

  • This structure represents a prepared statement. A statement is created by calling , which returns a statement handle, that is, a pointer to a . The handle is used for all subsequent statement-related functions until you close it with .

    The structure has no members that are for application use. Also, you should not try to make a copy of a structure. There is no guarantee that such a copy will be usable.

    Multiple statement handles can be associated with a single connection. The limit on the number of handles depends on the available system resources.

  • This structure is used both for statement input (data values sent to the server) and output (result values returned from the server). For input, it is used with to bind parameter data values to buffers for use by . For output, it is used with to bind result set buffers for use in fetching rows with .

    The structure contains the following members for use by application programs. Each is used both for input and for output, although sometimes for different purposes depending on the direction of data transfer.

    • The type of the buffer. The allowable values are listed later in this section. For input, indicates what type of value you are binding to a statement parameter. For output, it indicates what type of value you expect to receive in a result buffer.

    • For input, this is a pointer to the buffer in which a statement parameter's data value is stored. For output, it is a pointer to the buffer in which to return a result set column value. For numeric column types, should point to a variable of the proper C type. (If you are associating the variable with a column that has the attribute, the variable should be an C type. Indicate whether the variable is signed or unsigned by using the member, described later in this list.) For date and time column types, should point to a structure. For character and binary string column types, should point to a character buffer.

    • The actual size of in bytes. This indicates the maximum amount of data that can be stored in the buffer. For character and binary C data, the value specifies the length of when used with , or the maximum number of data bytes that can be fetched into the buffer when used with .

    • A pointer to an variable that indicates the actual number of bytes of data stored in . is used for character or binary C data. For input parameter data binding, points to an variable that indicates the length of the parameter value stored in ; this is used by . For output value binding, places the length of the column value that is returned into the variable that points to.

      is ignored for numeric and temporal data types because the length of the data value is determined by the value.

    • This member points to a variable that is true if a value is , false if it is not . For input, set to true to indicate that you are passing a value as a statement parameter. For output, this value is set to true after you fetch a row if the result set column value returned from the statement is .

    • This member is used for integer types. (These correspond to the , , , and type codes.) should be set to true for unsigned types and false for signed types.

    • For output, this member is used output to report data truncation errors. Truncation reporting must be enabled by calling with the option. When enabled, returns and is true in the structures for parameters in which truncation occurred. Truncation indicates loss of sign or significant digits, or that a string was too long to fit in a column. The member was added in MySQL 5.0.3.

    To use a structure, you should zero its contents to initialize it, and then set the members just described appropriately. For example, to declare and initialize an array of three structures, use this code:

    MYSQL_BIND    bind[3];
    memset(bind, 0, sizeof(bind));
    

  • This structure is used to send and receive , , , and data directly to and from the server. This is done by setting the member of a structure to one of the temporal types, and setting the member to point to a structure.

    The structure contains the following members:

    • The year.

    • The month of the year.

    • The day of the month.

    • The hour of the day.

    • The minute of the hour.

    • The second of the minute.

    • A boolean flag to indicate whether the time is negative.

    • The fractional part of the second. This member currently is unused.

    Only those parts of a structure that apply to a given type of temporal value are used: The , , and elements are used for , , and values. The , , and elements are used for , , and values. See Sección 24.3.10, “Manejo de valores de fecha y hora por parte de la API C”.

The following table shows the allowable values that may be specified in the member of structures. The table also shows those SQL types that correspond most closely to each value, and, for numeric and temporal types, the corresponding C type.

Value SQL Type C Type
 
 
 
 
 
 

Implicit type conversion may be performed in both directions.

24.3.6. Panorámica de las funciones de sentencias preparadas de la API C

Note: Some incompatible changes were made in MySQL 4.1.2. See Sección 24.3.7, “Descripciones de funciones de sentencias preparadas de la API C” for details.

The functions available for prepared statement processing are summarized here and described in greater detail in a later section. See Sección 24.3.7, “Descripciones de funciones de sentencias preparadas de la API C”.

Function Description
mysql_stmt_affected_rows() Returns the number of rows changes, deleted, or inserted by prepared , , or statement.
mysql_stmt_attr_get() Get value of an attribute for a prepared statement.
mysql_stmt_attr_set() Sets an attribute for a prepared statement.
mysql_stmt_bind_param() Associates application data buffers with the parameter markers in a prepared SQL statement.
mysql_stmt_bind_result() Associates application data buffers with columns in the result set.
mysql_stmt_close() Frees memory used by prepared statement.
mysql_stmt_data_seek() Seeks to an arbitrary row number in a statement result set.
mysql_stmt_errno() Returns the error number for the last statement execution.
mysql_stmt_error() Returns the error message for the last statement execution.
mysql_stmt_execute() Executes the prepared statement.
mysql_stmt_fetch() Fetches the next row of data from the result set and returns data for all bound columns.
mysql_stmt_fetch_column() Fetch data for one column of the current row of the result set.
mysql_stmt_field_count() Returns the number of result columns for the most recent statement.
mysql_stmt_free_result() Free the resources allocated to the statement handle.
mysql_stmt_init() Allocates memory for structure and initializes it.
mysql_stmt_insert_id() Returns the ID generated for an column by prepared statement.
mysql_stmt_num_rows() Returns total rows from the statement buffered result set.
mysql_stmt_param_count() Returns the number of parameters in a prepared SQL statement.
mysql_stmt_param_metadata() Return parameter metadata in the form of a result set.
mysql_stmt_prepare() Prepares an SQL string for execution.
mysql_stmt_reset() Reset the statement buffers in the server.
mysql_stmt_result_metadata() Returns prepared statement metadata in the form of a result set.
mysql_stmt_row_seek() Seeks to a row offset in a statement result set, using value returned from .
mysql_stmt_row_tell() Returns the statement row cursor position.
mysql_stmt_send_long_data() Sends long data in chunks to server.
mysql_stmt_sqlstate() Returns the SQLSTATE error code for the last statement execution.
mysql_stmt_store_result() Retrieves the complete result set to the client.

Call to create a statement handle, then to prepare it, to supply the parameter data, and to execute the statement. You can repeat the by changing parameter values in the respective buffers supplied through .

If the statement is a or any other statement that produces a result set, also returns the result set metadata information in the form of a result set through .

You can supply the result buffers using , so that the automatically returns data to these buffers. This is row-by-row fetching.

You can also send the text or binary data in chunks to server using . See Sección 24.3.7.25, “.

When statement execution has been completed, the statement handle must be closed using so that all resources associated with it can be freed.

If you obtained a statement's result set metadata by calling , you should also free the metadata using .

Execution Steps

To prepare and execute a statement, an application follows these steps:

  1. Create a prepared statement handle with . To prepare the statement on the server, call and pass it a string containing the SQL statement.

  2. If the statement produces a result set, call to obtain the result set metadata. This metadata is itself in the form of result set, albeit a separate one from the one that contains the rows returned by the query. The metadata result set indicates how many columns are in the result and contains information about each column.

  3. Set the values of any parameters using . All parameters must be set. Otherwise, statement execution returns an error or produces unexpected results.

  4. Call to execute the statement.

  5. If the statement produces a result set, bind the data buffers to use for retrieving the row values by calling .

  6. Fetch the data into the buffers row by row by calling repeatedly until no more rows are found.

  7. Repeat steps 3 through 6 as necessary, by changing the parameter values and re-executing the statement.

When is called, the MySQL client/server protocol performs these actions:

  • The server parses the statement and sends the okay status back to the client by assigning a statement ID. It also sends total number of parameters, a column count, and its metadata if it is a result set oriented statement. All syntax and semantics of the statement are checked by the server during this call.

  • The client uses this statement ID for the further operations, so that the server can identify the statement from among its pool of statements.

When is called, the MySQL client/server protocol performs these actions:

  • The client uses the statement handle and sends the parameter data to the server.

  • The server identifies the statement using the ID provided by the client, replaces the parameter markers with the newly supplied data, and executes the statement. If the statement produces a result set, the server sends the data back to the client. Otherwise, it sends an okay status and total number of rows changed, deleted, or inserted.

When is called, the MySQL client/server protocol performs these actions:

  • The client reads the data from the packet row by row and places it into the application data buffers by doing the necessary conversions. If the application buffer type is same as that of the field type returned from the server, the conversions are straightforward.

If an error occurs, you can get the statement error code, error message, and SQLSTATE value using , , and , respectively.

24.3.7. Descripciones de funciones de sentencias preparadas de la API C

To prepare and execute queries, use the functions in the following sections.

In MySQL 4.1.2, the names of several prepared statement functions were changed:

Old Name New Name

All functions that operate with a structure begin with the prefix .

Also in 4.1.2, the signature of the function was changed to . To create a handle, you should use the function.

24.3.7.1.

Description

Returns the total number of rows changed, deleted, or inserted by the last executed statement. May be called immediately after for , , or statements. For statements, works like .

This function was added in MySQL 4.1.0.

Return Values

An integer greater than zero indicates the number of rows affected or retrieved. Zero indicates that no records were updated for an statement, no rows matched the clause in the query, or that no query has yet been executed. -1 indicates that the query returned an error or that, for a query, was called prior to calling . Because returns an unsigned value, you can check for -1 by comparing the return value to (or to , which is equivalent).

See Sección 24.3.3.1, “ for additional information on the return value.

Errors

None.

Example

For the usage of , refer to the Example from Sección 24.3.7.10, “.

24.3.7.2.

Description

Can be used to get the current value for a statement attribute.

The argument is the option that you want to get; the should point to a variable that should contain the option value. If the option is an integer, then should point to the value of the integer.

See for a list of options and option types. See Sección 24.3.7.3, “.

This function was added in MySQL 4.1.2.

Return Values

if okay. Non-zero if is unknown.

Errors

None.

24.3.7.3.

Description

Can be used to set affect behavior for a statement. This function may be called multiple times to set several options.

The argument is the option that you want to set; the argument is the value for the option. If the option is an integer, then should point to the value of the integer.

Possible values:

Option Argument Type Function
If set to 1: Update metadata in .
Type of cursor to open for statement when is invoked. can be (the default) or .
Number of rows to fetch from server at a time when using a cursor. can be in the range from 1 to the maximum value of . The default is 1.

If you use the option with , a cursor is opened for the statement when you invoke . If there is already an open cursor from a previous call, it closes the cursor before opening a new one. also closes any open cursor before preparing the statement for re-execution. closes any open cursor.

This function was added in MySQL 4.1.2. The option was added in MySQL 5.0.2. The option was added in MySQL 5.0.6.

Return Values

if okay. Non-zero if is unknown.

Errors

None.

24.3.7.4.

Description

is used to bind data for the parameter markers in the SQL statement that was passed to . It uses structures to supply the data. is the address of an array of structures. The client library expects the array to contain an element for each '' parameter marker that is present in the query.

Suppose that you prepare the following statement:

INSERT INTO mytbl VALUES(?,?,?)

When you bind the parameters, the array of structures must contain three elements, and can be declared like this:

MYSQL_BIND bind[3];

The members of each element that should be set are described in Sección 24.3.5, “Tipos de datos de sentencias preparadas de la API C”.

This function was added in MySQL 4.1.2.

Return Values

Zero if the bind was successful. Non-zero if an error occurred.

Errors

  • Indicates if the bind is to supply the long data in chunks and if the buffer type is non string or binary.

  • The conversion is not supported. Possibly the value is illegal or is not one of the supported types.

  • Out of memory.

  • An unknown error occurred.

Example

For the usage of , refer to the Example from Sección 24.3.7.10, “.

24.3.7.5.

Description

is used to associate (bind) columns in the result set to data buffers and length buffers. When is called to fetch data, the MySQL client/server protocol places the data for the bound columns into the specified buffers.

All columns must be bound to buffers prior to calling . is the address of an array of structures. The client library expects the array to contain an element for each column of the result set. If you do not bind columns to structures, simply ignores the data fetch. The buffers should be large enough to hold the data values, because the protocol doesn't return data values in chunks.

A column can be bound or rebound at any time, even after a result set has been partially retrieved. The new binding takes effect the next time is called. Suppose that an application binds the columns in a result set and calls . The client/server protocol returns data in the bound buffers. Then suppose that the application binds the columns to a different set of buffers. The protocol does not place data into the newly bound buffers until the next call to occurs.

To bind a column, an application calls and passes the type, address, and the address of the length buffer. The members of each element that should be set are described in Sección 24.3.5, “Tipos de datos de sentencias preparadas de la API C”.

This function was added in MySQL 4.1.2.

Return Values

Zero if the bind was successful. Non-zero if an error occurred.

Errors

  • The conversion is not supported. Possibly the value is illegal or is not one of the supported types.

  • Out of memory.

  • An unknown error occurred.

Example

For the usage of , refer to the Example from Sección 24.3.7.13, “.

24.3.7.6.

Description

Closes the prepared statement. also deallocates the statement handle pointed to by .

If the current statement has pending or unread results, this function cancels them so that the next query can be executed.

This function was added in MySQL 4.1.0.

Return Values

Zero if the statement was freed successfully. Non-zero if an error occurred.

Errors

  • The MySQL server has gone away.

  • An unknown error occurred.

Example

For the usage of , refer to the Example from Sección 24.3.7.10, “.

24.3.7.7.

Description

Seeks to an arbitrary row in a statement result set. The value is a row number and should be in the range from to .

This function requires that the statement result set structure contains the entire result of the last executed query, so may be used only in conjunction with .

This function was added in MySQL 4.1.1.

Return Values

None.

Errors

None.

24.3.7.8.

Description

For the statement specified by , returns the error code for the most recently invoked statement API function that can succeed or fail. A return value of zero means that no error occurred. Client error message numbers are listed in the MySQL header file. Server error message numbers are listed in . In the MySQL source distribution you can find a complete list of error messages and error numbers in the file . The server error codes also are listed at Capítulo 26, Manejo de errores en MySQL.

This function was added in MySQL 4.1.0.

Return Values

An error code value. Zero if no error occurred.

Errors

None.

24.3.7.9.

Description

For the statement specified by , returns a null-terminated string containing the error message for the most recently invoked statement API function that can succeed or fail. An empty string () is returned if no error occurred. This means the following two tests are equivalent:

if (mysql_stmt_errno(stmt))
{
  // an error occurred
}

if (mysql_stmt_error(stmt)[0])
{
  // an error occurred
}

The language of the client error messages may be changed by recompiling the MySQL client library. Currently you can choose error messages in several different languages.

This function was added in MySQL 4.1.0.

Return Values

A character string that describes the error. An empty string if no error occurred.

Errors

None.

24.3.7.10.

Description

executes the prepared query associated with the statement handle. The currently bound parameter marker values are sent to server during this call, and the server replaces the markers with this newly supplied data.

If the statement is an , , or , the total number of changed, deleted, or inserted rows can be found by calling . If this is a statement such as that generates a result set, you must call to fetch the data prior to calling any other functions that result in query processing. For more information on how to fetch the results, refer to Sección 24.3.7.13, “.

For statements that generate a result set, you can request that open a cursor for the statement by calling before executing the statement. If you execute a statement multiple times, closes any open cursor before opening a new one.

This function was added in MySQL 4.1.2. Cursor support was added in MySQL 5.

Return Values

Zero if execution was successful. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • Out of memory.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

Example

The following example demonstrates how to create and populate a table using , , , , , and . The variable is assumed to be a valid connection handle.

#define STRING_SIZE 50

#define DROP_SAMPLE_TABLE "DROP TABLE IF EXISTS test_table"
#define CREATE_SAMPLE_TABLE "CREATE TABLE test_table(col1 INT,\
                                                 col2 VARCHAR(40),\
                                                 col3 SMALLINT,\
                                                 col4 TIMESTAMP)"
#define INSERT_SAMPLE "INSERT INTO test_table(col1,col2,col3) VALUES(?,?,?)"

MYSQL_STMT    *stmt;
MYSQL_BIND    bind[3];
my_ulonglong  affected_rows;
int           param_count;
short         small_data;
int           int_data;
char          str_data[STRING_SIZE];
unsigned long str_length;
my_bool       is_null;

if (mysql_query(mysql, DROP_SAMPLE_TABLE))
{
  fprintf(stderr, " DROP TABLE failed\n");
  fprintf(stderr, " %s\n", mysql_error(mysql));
  exit(0);
}

if (mysql_query(mysql, CREATE_SAMPLE_TABLE))
{
  fprintf(stderr, " CREATE TABLE failed\n");
  fprintf(stderr, " %s\n", mysql_error(mysql));
  exit(0);
}

/* Prepare an INSERT query with 3 parameters */
/* (the TIMESTAMP column is not named; the server */
/*  sets it to the current date and time) */
stmt = mysql_stmt_init(mysql);
if (!stmt)
{
  fprintf(stderr, " mysql_stmt_init(), out of memory\n");
  exit(0);
}
if (mysql_stmt_prepare(stmt, INSERT_SAMPLE, strlen(INSERT_SAMPLE)))
{
  fprintf(stderr, " mysql_stmt_prepare(), INSERT failed\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}
fprintf(stdout, " prepare, INSERT successful\n");

/* Get the parameter count from the statement */
param_count= mysql_stmt_param_count(stmt);
fprintf(stdout, " total parameters in INSERT: %d\n", param_count);

if (param_count != 3) /* validate parameter count */
{
  fprintf(stderr, " invalid parameter count returned by MySQL\n");
  exit(0);
}

/* Bind the data for all 3 parameters */

memset(bind, 0, sizeof(bind));

/* INTEGER PARAM */
/* This is a number type, so there is no need to specify buffer_length */
bind[0].buffer_type= MYSQL_TYPE_LONG;
bind[0].buffer= (char *)&int_data;
bind[0].is_null= 0;
bind[0].length= 0;

/* STRING PARAM */
bind[1].buffer_type= MYSQL_TYPE_STRING;
bind[1].buffer= (char *)str_data;
bind[1].buffer_length= STRING_SIZE;
bind[1].is_null= 0;
bind[1].length= &str_length;

/* SMALLINT PARAM */
bind[2].buffer_type= MYSQL_TYPE_SHORT;
bind[2].buffer= (char *)&small_data;
bind[2].is_null= &is_null;
bind[2].length= 0;

/* Bind the buffers */
if (mysql_stmt_bind_param(stmt, bind))
{
  fprintf(stderr, " mysql_stmt_bind_param() failed\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

/* Specify the data values for the first row */
int_data= 10;             /* integer */
strncpy(str_data, "MySQL", STRING_SIZE); /* string  */
str_length= strlen(str_data);

/* INSERT SMALLINT data as NULL */
is_null= 1;

/* Execute the INSERT statement - 1*/
if (mysql_stmt_execute(stmt))
{
  fprintf(stderr, " mysql_stmt_execute(), 1 failed\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

/* Get the total number of affected rows */
affected_rows= mysql_stmt_affected_rows(stmt);
fprintf(stdout, " total affected rows(insert 1): %lu\n",
                (unsigned long) affected_rows);

if (affected_rows != 1) /* validate affected rows */
{
  fprintf(stderr, " invalid affected rows by MySQL\n");
  exit(0);
}

/* Specify data values for second row, then re-execute the statement */
int_data= 1000;
strncpy(str_data, "The most popular Open Source database", STRING_SIZE);
str_length= strlen(str_data);
small_data= 1000;         /* smallint */
is_null= 0;               /* reset */

/* Execute the INSERT statement - 2*/
if (mysql_stmt_execute(stmt))
{
  fprintf(stderr, " mysql_stmt_execute, 2 failed\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

/* Get the total rows affected */
affected_rows= mysql_stmt_affected_rows(stmt);
fprintf(stdout, " total affected rows(insert 2): %lu\n",
                (unsigned long) affected_rows);

if (affected_rows != 1) /* validate affected rows */
{
  fprintf(stderr, " invalid affected rows by MySQL\n");
  exit(0);
}

/* Close the statement */
if (mysql_stmt_close(stmt))
{
  fprintf(stderr, " failed while closing the statement\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

Note: For complete examples on the use of prepared statement functions, refer to the file . This file can be obtained from a MySQL source distribution or from the BitKeeper source repository.

24.3.7.11.

Description

Releases memory associated with the result set produced by execution of the prepared statement. If there is a cursor open for the statement, closes it.

This function was added in MySQL 4.1.1. Cursor support was added in MySQL 5.

Return Values

Zero if the result set was freed successfully. Non-zero if an error occurred.

Errors

24.3.7.12.

Description

Returns the value generated for an column by the prepared or statement. Use this function after you have executed prepared statement into a table which contains an field.

See Sección 24.3.3.34, “ for more information.

This function was added in MySQL 4.1.2.

Return Values

Value for column which was automatically generated or explicitly set during execution of prepared statement, or value generated by ) function. Return value is undefined if statement does not set value.

Errors

None.

24.3.7.13.

Description

returns the next row in the result set. It can be called only while the result set exists, that is, after a call to that creates a result set or after , which is called after to buffer the entire result set.

returns row data using the buffers bound by . It returns the data in those buffers for all the columns in the current row set and the lengths are returned to the pointer.

All columns must be bound by the application before calling .

If a fetched data value is a value, the value of the corresponding structure contains TRUE (1). Otherwise, the data and its length are returned in the and elements based on the buffer type specified by the application. Each numeric and temporal type has a fixed length, as listed in the following table. The length of the string types depends on the length of the actual data value, as indicated by .

Type Length
1
2
4
8
4
8

This function was added in MySQL 4.1.2.

Return Values

Return Value Description
0 Successful, the data has been fetched to application data buffers.
1 Error occurred. Error code and message can be obtained by calling and .
No more rows/data exists
Data truncation occurred

is not returned unless truncation reporting is enabled with . To determine which parameters were truncated when this value is returned, check the members of the parameter structures.

Errors

  • Commands were executed in an improper order.

  • Out of memory.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

  • The buffer type is , , , or , but the data type is not , , , or .

  • All other unsupported conversion errors are returned from .

Example

The following example demonstrates how to fetch data from a table using , , and . (This example expects to retrieve the two rows inserted by the example shown in Sección 24.3.7.10, “.) The variable is assumed to be a valid connection handle.

#define STRING_SIZE 50

#define SELECT_SAMPLE "SELECT col1, col2, col3, col4 FROM test_table"

MYSQL_STMT    *stmt;
MYSQL_BIND    bind[4];
MYSQL_RES     *prepare_meta_result;
MYSQL_TIME    ts;
unsigned long length[4];
int           param_count, column_count, row_count;
short         small_data;
int           int_data;
char          str_data[STRING_SIZE];
my_bool       is_null[4];

/* Prepare a SELECT query to fetch data from test_table */
stmt = mysql_stmt_init(mysql);
if (!stmt)
{
  fprintf(stderr, " mysql_stmt_init(), out of memory\n");
  exit(0);
}
if (mysql_stmt_prepare(stmt, SELECT_SAMPLE, strlen(SELECT_SAMPLE)))
{
  fprintf(stderr, " mysql_stmt_prepare(), SELECT failed\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}
fprintf(stdout, " prepare, SELECT successful\n");

/* Get the parameter count from the statement */
param_count= mysql_stmt_param_count(stmt);
fprintf(stdout, " total parameters in SELECT: %d\n", param_count);

if (param_count != 0) /* validate parameter count */
{
  fprintf(stderr, " invalid parameter count returned by MySQL\n");
  exit(0);
}

/* Fetch result set meta information */
prepare_meta_result = mysql_stmt_result_metadata(stmt);
if (!prepare_meta_result)
{
  fprintf(stderr,
         " mysql_stmt_result_metadata(), returned no meta information\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

/* Get total columns in the query */
column_count= mysql_num_fields(prepare_meta_result);
fprintf(stdout, " total columns in SELECT statement: %d\n", column_count);

if (column_count != 4) /* validate column count */
{
  fprintf(stderr, " invalid column count returned by MySQL\n");
  exit(0);
}

/* Execute the SELECT query */
if (mysql_stmt_execute(stmt))
{
  fprintf(stderr, " mysql_stmt_execute(), failed\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

/* Bind the result buffers for all 4 columns before fetching them */

memset(bind, 0, sizeof(bind));

/* INTEGER COLUMN */
bind[0].buffer_type= MYSQL_TYPE_LONG;
bind[0].buffer= (char *)&int_data;
bind[0].is_null= &is_null[0];
bind[0].length= &length[0];

/* STRING COLUMN */
bind[1].buffer_type= MYSQL_TYPE_STRING;
bind[1].buffer= (char *)str_data;
bind[1].buffer_length= STRING_SIZE;
bind[1].is_null= &is_null[1];
bind[1].length= &length[1];

/* SMALLINT COLUMN */
bind[2].buffer_type= MYSQL_TYPE_SHORT;
bind[2].buffer= (char *)&small_data;
bind[2].is_null= &is_null[2];
bind[2].length= &length[2];

/* TIMESTAMP COLUMN */
bind[3].buffer_type= MYSQL_TYPE_TIMESTAMP;
bind[3].buffer= (char *)&ts;
bind[3].is_null= &is_null[3];
bind[3].length= &length[3];

/* Bind the result buffers */
if (mysql_stmt_bind_result(stmt, bind))
{
  fprintf(stderr, " mysql_stmt_bind_result() failed\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

/* Now buffer all results to client */
if (mysql_stmt_store_result(stmt))
{
  fprintf(stderr, " mysql_stmt_store_result() failed\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

/* Fetch all rows */
row_count= 0;
fprintf(stdout, "Fetching results ...\n");
while (!mysql_stmt_fetch(stmt))
{
  row_count++;
  fprintf(stdout, "  row %d\n", row_count);

  /* column 1 */
  fprintf(stdout, "   column1 (integer)  : ");
  if (is_null[0])
    fprintf(stdout, " NULL\n");
  else
    fprintf(stdout, " %d(%ld)\n", int_data, length[0]);

  /* column 2 */
  fprintf(stdout, "   column2 (string)   : ");
  if (is_null[1])
    fprintf(stdout, " NULL\n");
  else
    fprintf(stdout, " %s(%ld)\n", str_data, length[1]);

  /* column 3 */
  fprintf(stdout, "   column3 (smallint) : ");
  if (is_null[2])
    fprintf(stdout, " NULL\n");
  else
    fprintf(stdout, " %d(%ld)\n", small_data, length[2]);

  /* column 4 */
  fprintf(stdout, "   column4 (timestamp): ");
  if (is_null[3])
    fprintf(stdout, " NULL\n");
  else
    fprintf(stdout, " %04d-%02d-%02d %02d:%02d:%02d (%ld)\n",
                     ts.year, ts.month, ts.day,
                     ts.hour, ts.minute, ts.second,
                     length[3]);
  fprintf(stdout, "\n");
}

/* Validate rows fetched */
fprintf(stdout, " total rows fetched: %d\n", row_count);
if (row_count != 2)
{
  fprintf(stderr, " MySQL failed to return all rows\n");
  exit(0);
}

/* Free the prepared result metadata */
mysql_free_result(prepare_meta_result);


/* Close the statement */
if (mysql_stmt_close(stmt))
{
  fprintf(stderr, " failed while closing the statement\n");
  fprintf(stderr, " %s\n", mysql_stmt_error(stmt));
  exit(0);
}

24.3.7.14.

Description

Fetch one column from the current result set row. provides the buffer where data should be placed. It should be set up the same way as for . indicates which column to fetch. The first column is numbered 0. is the offset within the data value at which to begin retrieving data. This can be used for fetching the data value in pieces. The beginning of the value is offset 0.

This function was added in MySQL 4.1.2.

Return Values

Zero if the value was fetched successfully. Non-zero if an error occurred.

Errors

  • Invalid column number.

  • The end of the result set has already been reached.

24.3.7.15.

Description

Returns the number of columns for the most recent statement for the statement handler. This value is zero for statements such as or that do not produce result sets.

can be called after you have prepared a statement by invoking .

This function was added in MySQL 4.1.3.

Return Values

An unsigned integer representing the number of columns in a result set.

Errors

None.

24.3.7.16.

Description

Create a handle. The handle should be freed with .

This function was added in MySQL 4.1.2.

Return values

A pointer to a structure in case of success. if out of memory.

Errors

  • Out of memory.

24.3.7.17.

Description

Returns the number of rows in the result set.

The use of depends on whether or not you used to buffer the entire result set in the statement handle.

If you use , may be called immediately.

This function was added in MySQL 4.1.1.

Return Values

The number of rows in the result set.

Errors

None.

24.3.7.18.

Description

Returns the number of parameter markers present in the prepared statement.

This function was added in MySQL 4.1.2.

Return Values

An unsigned long integer representing the number of parameters in a statement.

Errors

None.

Example

For the usage of , refer to the Example from Sección 24.3.7.10, “.

24.3.7.19.

To be added.

This function was added in MySQL 4.1.2.

Description

Return Values

Errors

24.3.7.20.

Description

Given the statement handle returned by , prepares the SQL statement pointed to by the string and returns a status value. The string length should be given by the argument. The string must consist of a single SQL statement. You should not add a terminating semicolon ('') or to the statement.

The application can include one or more parameter markers in the SQL statement by embedding question mark ('') characters into the SQL string at the appropriate positions.

The markers are legal only in certain places in SQL statements. For example, they are allowed in the list of an statement (to specify column values for a row), or in a comparison with a column in a clause to specify a comparison value. However, they are not allowed for identifiers (such as table or column names), or to specify both operands of a binary operator such as the equal sign. The latter restriction is necessary because it would be impossible to determine the parameter type. In general, parameters are legal only in Data Manipulation Language (DML) statements, and not in Data Definition Language (DDL) statements.

The parameter markers must be bound to application variables using before executing the statement.

This function was added in MySQL 4.1.2.

Return Values

Zero if the statement was prepared successfully. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • Out of memory.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query

  • An unknown error occurred.

If the prepare operation was unsuccessful (that is, returns non-zero), the error message can be obtained by calling .

Example

For the usage of , refer to the Example from Sección 24.3.7.10, “.

24.3.7.21.

Description

Reset the prepared statement on the client and server to state after prepare. This is mainly used to reset data sent with . Any open cursor for the statement is closed.

To re-prepare the statement with another query, use .

This function was added in MySQL 4.1.1. Cursor support was added in MySQL 5.

Return Values

Zero if the statement was reset successfully. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query

  • An unknown error occurred.

24.3.7.22.

Description

If a statement passed to is one that produces a result set, returns the result set metadata in the form of a pointer to a structure that can be used to process the meta information such as total number of fields and individual field information. This result set pointer can be passed as an argument to any of the field-based API functions that process result set metadata, such as:

The result set structure should be freed when you are done with it, which you can do by passing it to . This is similar to the way you free a result set obtained from a call to .

The result set returned by contains only metadata. It does not contain any row results. The rows are obtained by using the statement handle with .

This function was added in MySQL 4.1.2.

Return Values

A result structure. if no meta information exists for the prepared query.

Errors

  • Out of memory.

  • An unknown error occurred.

Example

For the usage of , refer to the Example from Sección 24.3.7.13, “.

24.3.7.23.

Description

Sets the row cursor to an arbitrary row in a statement result set. The value is a row offset that should be a value returned from or from . This value is not a row number; if you want to seek to a row within a result set by number, use instead.

This function requires that the result set structure contains the entire result of the query, so may be used only in conjunction with .

This function was added in MySQL 4.1.1.

Return Values

The previous value of the row cursor. This value may be passed to a subsequent call to .

Errors

None.

24.3.7.24.

Description

Returns the current position of the row cursor for the last . This value can be used as an argument to .

You should use only after .

This function was added in MySQL 4.1.1.

Return Values

The current offset of the row cursor.

Errors

None.

24.3.7.25.

Description

Allows an application to send parameter data to the server in pieces (or “chunks”). This function can be called multiple times to send the parts of a character or binary data value for a column, which must be one of the or data types.

indicates which parameter to associate the data with. Parameters are numbered beginning with 0. is a pointer to a buffer containing data to be sent, and indicates the number of bytes in the buffer.

Note: The next call ignores the bind buffer for all parameters that have been used with since last or .

If you want to reset/forget the sent data, you can do it with . See Sección 24.3.7.21, “.

This function was added in MySQL 4.1.2.

Return Values

Zero if the data is sent successfully to server. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • The MySQL server has gone away.

  • Out of memory.

  • An unknown error occurred.

Example

The following example demonstrates how to send the data for a column in chunks. It inserts the data value into the column. The variable is assumed to be a valid connection handle.

#define INSERT_QUERY "INSERT INTO test_long_data(text_column) VALUES(?)"

MYSQL_BIND bind[1];
long       length;

smtt = mysql_stmt_init(mysql);
if (!stmt)
{
  fprintf(stderr, " mysql_stmt_init(), out of memory\n");
  exit(0);
}
if (mysql_stmt_prepare(stmt, INSERT_QUERY, strlen(INSERT_QUERY)))
{
  fprintf(stderr, "\n mysql_stmt_prepare(), INSERT failed");
  fprintf(stderr, "\n %s", mysql_stmt_error(stmt));
  exit(0);
}
 memset(bind, 0, sizeof(bind));
 bind[0].buffer_type= MYSQL_TYPE_STRING;
 bind[0].length= &length;
 bind[0].is_null= 0;

/* Bind the buffers */
if (mysql_stmt_bind_param(stmt, bind))
{
  fprintf(stderr, "\n param bind failed");
  fprintf(stderr, "\n %s", mysql_stmt_error(stmt));
  exit(0);
}

 /* Supply data in chunks to server */
 if (!mysql_stmt_send_long_data(stmt,0,"MySQL",5))
{
  fprintf(stderr, "\n send_long_data failed");
  fprintf(stderr, "\n %s", mysql_stmt_error(stmt));
  exit(0);
}

 /* Supply the next piece of data */
 if (mysql_stmt_send_long_data(stmt,0," - The most popular Open Source database",40))
{
  fprintf(stderr, "\n send_long_data failed");
  fprintf(stderr, "\n %s", mysql_stmt_error(stmt));
  exit(0);
}

 /* Now, execute the query */
 if (mysql_stmt_execute(stmt))
{
  fprintf(stderr, "\n mysql_stmt_execute failed");
  fprintf(stderr, "\n %s", mysql_stmt_error(stmt));
  exit(0);
}

24.3.7.26.

Description

For the statement specified by , returns a null-terminated string containing the SQLSTATE error code for the most recently invoked prepared statement API function that can succeed or fail. The error code consists of five characters. means “no error.” The values are specified by ANSI SQL and ODBC. For a list of possible values, see Capítulo 26, Manejo de errores en MySQL.

Note that not all MySQL errors are yet mapped to SQLSTATE's. The value (general error) is used for unmapped errors.

This function was added to MySQL 4.1.1.

Return Values

A null-terminated character string containing the SQLSTATE error code.

24.3.7.27.

Description

You must call for every statement that successfully produces a result set (, , , ), and only if you want to buffer the complete result set by the client, so that the subsequent call returns buffered data.

It is unnecessary to call for other statements, but if you do, it does not harm or cause any notable performance problem. You can detect whether the statement produced a result set by checking if returns . For more information, refer to Sección 24.3.7.22, “.

Note: MySQL doesn't by default calculate for all columns in because calculating this would slow down considerably and most applications doesn't need . If you want to be updated, you can call to enable this. See Sección 24.3.7.3, “.

This function was added in MySQL 4.1.0.

Return Values

Zero if the results are buffered successfully. Non-zero if an error occurred.

Errors

  • Commands were executed in an improper order.

  • Out of memory.

  • The MySQL server has gone away.

  • The connection to the server was lost during the query.

  • An unknown error occurred.

24.3.8. Problemas con sentencias preparadas de la API C

Here follows a list of the currently known problems with prepared statements:

  • , , and don't support sub seconds (for example from .

  • When converting an integer to string, is honored with prepared statements in some cases where the MySQL server doesn't print the leading zeros. (For example, with ).

  • When converting a floating point number to a string in the client, the value may be slightly different in the last digits.

  • Prepared statements do not use the Query Cache, even in cases where a query does not contain any placeholders. See Sección 5.12.1, “Cómo opera la caché de consultas”.

24.3.9. Tratamiento por parte de la API C de la ejecución de múltiples consultas

From version 4.1, MySQL supports the execution of multiple statements specified in a single query string. To use this capability with a given connection, you must specify the option in the flags parameter of when opening the connection. You can also set this for an existing connection by calling

By default, and return only the first query status and the subsequent queries status can be processed using and .

/* Connect to server with option CLIENT_MULTI_STATEMENTS */
mysql_real_connect(..., CLIENT_MULTI_STATEMENTS);

/* Now execute multiple queries */
mysql_query(mysql,"DROP TABLE IF EXISTS test_table;\
                   CREATE TABLE test_table(id INT);\
                   INSERT INTO test_table VALUES(10);\
                   UPDATE test_table SET id=20 WHERE id=10;\
                   SELECT * FROM test_table;\
                   DROP TABLE test_table");
do
{
  /* Process all results */
  ...
  printf("total affected rows: %lld", mysql_affected_rows(mysql));
  ...
  if (!(result= mysql_store_result(mysql)))
  {
     printf(stderr, "Got fatal error processing query\n");
     exit(1);
  }
  process_result_set(result); /* client function */
  mysql_free_result(result);
} while (!mysql_next_result(mysql));

The multiple-statement capability can be used with or . It cannot be used with the prepared statement interface. Prepared statement handles are defined to work only with strings that contain a single statement.

24.3.10. Manejo de valores de fecha y hora por parte de la API C

The new binary protocol available in MySQL 4.1 and above allows you to send and receive date and time values (, , , and ), using the structure. The members of this structure are described in Sección 24.3.5, “Tipos de datos de sentencias preparadas de la API C”.

To send temporal data values, you create a prepared statement with . Then, before calling to execute the statement, use the following procedure to set up each temporal parameter:

  1. In the structure associated with the data value, set the member to the type that indicates what kind of temporal value you're sending. For , , , or values, set to , , , or , respectively.

  2. Set the member of the structure to the address of the structure in which you pass the temporal value.

  3. Fill in the members of the structure that are appropriate for the type of temporal value you're passing.

Use to bind the parameter data to the statement. Then you can call .

To retrieve temporal values, the procedure is similar, except that you set the member to the type of value you expect to receive, and the member to the address of a structure into which the returned value should be placed. Use to bind the buffers to the statement after calling and before fetching the results.

Here is a simple example that inserts , , and data. The variable is assumed to be a valid connection handle.

  MYSQL_TIME  ts;
  MYSQL_BIND  bind[3];
  MYSQL_STMT  *stmt;

  strmov(query, "INSERT INTO test_table(date_field, time_field,
                                        timestamp_field) VALUES(?,?,?");

  stmt = mysql_stmt_init(mysql);
  if (!stmt)
  {
    fprintf(stderr, " mysql_stmt_init(), out of memory\n");
    exit(0);
  }
  if (mysql_stmt_prepare(mysql, query, strlen(query)))
  {
    fprintf(stderr, "\n mysql_stmt_prepare(), INSERT failed");
    fprintf(stderr, "\n %s", mysql_stmt_error(stmt));
    exit(0);
  }

  /* set up input buffers for all 3 parameters */
  bind[0].buffer_type= MYSQL_TYPE_DATE;
  bind[0].buffer= (char *)&ts;
  bind[0].is_null= 0;
  bind[0].length= 0;
  ...
  bind[1]= bind[2]= bind[0];
  ...

  mysql_stmt_bind_param(stmt, bind);

  /* supply the data to be sent in the ts structure */
  ts.year= 2002;
  ts.month= 02;
  ts.day= 03;

  ts.hour= 10;
  ts.minute= 45;
  ts.second= 20;

  mysql_stmt_execute(stmt);
  ..

24.3.11. Descripción de funciones de la API C para el control de subprocesos

You need to use the following functions when you want to create a threaded client. See Sección 24.3.15, “Cómo hacer un cliente multihilo”.

24.3.11.1.

Description

This function needs to be called once in the program before calling any MySQL function. This initializes some global variables that MySQL needs. If you are using a thread-safe client library, this also calls for this thread.

This is automatically called by , , and .

Return Values

None.

24.3.11.2.

Description

This function needs to be called for each created thread to initialize thread-specific variables.

This is automatically called by and .

Return Values

Zero if successful. Non-zero if an error occurred.

24.3.11.3.

Description

This function needs to be called before calling to free memory allocated by .

Note that this function is not invoked automatically by the client library. It must be called explicitly to avoid a memory leak.

Return Values

None.

24.3.11.4.

Description

This function indicates whether the client is compiled as thread-safe.

Return Values

1 is the client is thread-safe, 0 otherwise.

24.3.12. Descripción de las funciones de la API C del servidor incrustado (embedded)

If you want to allow your application to be linked against the embedded MySQL server library, you must use the and functions. See Sección 24.3.16, “libmysqld, la biblioteca del servidor MySQL incrustado (embedded)”.

However, to provide improved memory management, even programs that are linked with rather than should include calls to begin and end use of the library. As of MySQL 4.1.10 and 5.0.3, the and functions can be used to do this. These actually are symbols that make them equivalent to and , but the names more clearly indicate that they should be called when beginning and ending use of a MySQL C API library no matter whether the application uses or . For more information, see Sección 24.3.2, “Panorámica de funciones de la API C”.

24.3.12.1.

Description

This function must be called once in the program using the embedded server before calling any other MySQL function. It starts the server and initializes any subsystems (, , etc.) that the server uses. If this function is not called, the next call to executes . If you are using the DBUG package that comes with MySQL, you should call this after you have called .

The and arguments are analogous to the arguments to . The first element of is ignored (it typically contains the program name). For convenience, may be (zero) if there are no command-line arguments for the server. makes a copy of the arguments so it's safe to destroy or after the call.

If you want to connect to an external server without starting the embedded server, you have to specify a negative value for .

The -terminated list of strings in selects which groups in the option files are active. See Sección 4.3.2, “Usar ficheros de opciones”. For convenience, may be , in which case the and groups are active.

Example

#include <mysql.h>
#include <stdlib.h>

static char *server_args[] = {
  "this_program",       /* this string is not used */
  "--datadir=.",
  "--key_buffer_size=32M"
};
static char *server_groups[] = {
  "embedded",
  "server",
  "this_program_SERVER",
  (char *)NULL
};

int main(void) {
  if (mysql_server_init(sizeof(server_args) / sizeof(char *),
                        server_args, server_groups))
    exit(1);

  /* Use any MySQL API functions here */

  mysql_server_end();

  return EXIT_SUCCESS;
}

Return Values

0 if okay, 1 if an error occurred.

24.3.12.2.

Description

This function must be called once in the program after all other MySQL functions. It shuts down the embedded server.

Return Values

None.

24.3.13. Preguntas y problemas comunes en el uso de la API C

24.3.13.1. ¿Por qué a veces devuelve después de que haya dado un resultado?

It is possible for to return following a successful call to . When this happens, it means one of the following conditions occurred:

  • There was a failure (for example, if the result set was too large).

  • The data couldn't be read (an error occurred on the connection).

  • The query returned no data (for example, it was an , , or ).

You can always check whether the statement should have produced a non-empty result by calling . If returns zero, the result is empty and the last query was a statement that does not return values (for example, an or a ). If returns a non-zero value, the statement should have produced a non-empty result. See the description of the function for an example.

You can test for an error by calling or .

24.3.13.2. Qué resultados se puede obtener de una consulta

In addition to the result set returned by a query, you can also get the following information:

  • returns the number of rows affected by the last query when doing an , , or .

    In MySQL 3.23, there is an exception when is used without a clause. In this case, the table is re-created as an empty table and returns zero for the number of records affected. In MySQL 4.0, always returns the correct number of rows deleted. For a fast recreate, use .

  • returns the number of rows in a result set. With , may be called as soon as returns. With , may be called only after you have fetched all the rows with .

  • returns the ID generated by the last query that inserted a row into a table with an index. See Sección 24.3.3.34, “.

  • Some queries (, , ) return additional information. The result is returned by . See the description for for the format of the string that it returns. returns a pointer if there is no additional information.

24.3.13.3. Cómo obtener el ID único del último registro insertado

If you insert a record into a table that contains an column, you can obtain the value stored into that column by calling the function.

You can check from your C applications whether a value was stored into an column by executing the following code (which assumes that you've checked that the statement succeeded). It determines whether the query was an with an index:

if ((result = mysql_store_result(&mysql)) == 0 &&
    mysql_field_count(&mysql) == 0 &&
    mysql_insert_id(&mysql) != 0)
{
    used_id = mysql_insert_id(&mysql);
}

For more information, see Sección 24.3.3.34, “.

When a new value has been generated, you can also obtain it by executing a statement with and retrieving the value from the result set returned by the statement.

For , the most recently generated ID is maintained in the server on a per-connection basis. It is not changed by another client. It is not even changed if you update another column with a non-magic value (that is, a value that is not and not ).

If you want to use the ID that was generated for one table and insert it into a second table, you can use SQL statements like this:

INSERT INTO foo (auto,text)
    VALUES(NULL,'text');              # generate ID by inserting NULL
INSERT INTO foo2 (id,text)
    VALUES(LAST_INSERT_ID(),'text');  # use ID in second table

Note that returns the value stored into an column, whether that value is automatically generated by storing or or was specified as an explicit value. returns only automatically generated values. If you store an explicit value other than or , it does not affect the value returned by .

24.3.13.4. Problemas enlazando con la API C

When linking with the C API, the following errors may occur on some systems:

gcc -g -o client test.o -L/usr/local/lib/mysql -lmysqlclient -lsocket -lnsl

Undefined        first referenced
 symbol          in file
floor            /usr/local/lib/mysql/libmysqlclient.a(password.o)
ld: fatal: Symbol referencing errors. No output written to client

If this happens on your system, you must include the math library by adding to the end of the compile/link line.

24.3.14. Generar programas cliente

If you compile MySQL clients that you've written yourself or that you obtain from a third-party, they must be linked using the option on the link command. You may also need to specify a option to tell the linker where to find the library. For example, if the library is installed in , use on the link command.

For clients that use MySQL header files, you may need to specify a option when you compile them (for example, ), so the compiler can find the header files.

To make it simpler to compile MySQL programs on Unix, we have provided the mysql_config script for you. See Sección 24.2, “mysql_config — ”.

You can use it to compile a MySQL client as follows:

CFG=/usr/local/mysql/bin/mysql_config
sh -c "gcc -o progname `$CFG --cflags` progname.c `$CFG --libs`"

The is needed to get the shell not to treat the output from mysql_config as one word.

24.3.15. Cómo hacer un cliente multihilo

The client library is almost thread-safe. The biggest problem is that the subroutines in that read from sockets are not interrupt safe. This was done with the thought that you might want to have your own alarm that can break a long read to a server. If you install interrupt handlers for the interrupt, the socket handling should be thread-safe.

New in 4.0.16: To not abort the program when a connection terminates, MySQL blocks on the first call to (), or . If you want to have your own handler, you should first call and then install your handler. In older versions of MySQL was blocked, but only in the thread safe client library, for every call to .

In the older binaries we distribute on our Web site (http://www.mysql.com/), the client libraries are not normally compiled with the thread-safe option (the Windows binaries are by default compiled to be thread-safe). Newer binary distributions should have both a normal and a thread-safe client library.

To get a threaded client where you can interrupt the client from other threads and set timeouts when talking with the MySQL server, you should use the , , and libraries and the code that the server uses.

If you don't need interrupts or timeouts, you can just compile a thread-safe client library and use this. See Sección 24.3, “La API C de MySQL”. In this case, you don't have to worry about the object file or the other MySQL libraries.

When using a threaded client and you want to use timeouts and interrupts, you can make great use of the routines in the file. If you are using routines from the library, the only thing you must remember is to call first! See Sección 24.3.11, “Descripción de funciones de la API C para el control de subprocesos”.

All functions except are by default thread-safe. The following notes describe how to compile a thread-safe client library and use it in a thread-safe manner. (The notes below for actually apply to as well, but because is deprecated, you should be using anyway.)

To make thread-safe, you must recompile the client library with this command:

shell> ./configure --enable-thread-safe-client

This creates a thread-safe client library . (Assuming that your OS has a thread-safe function.) This library is thread-safe per connection. You can let two threads share the same connection with the following caveats:

  • Two threads can't send a query to the MySQL server at the same time on the same connection. In particular, you have to ensure that between a and no other thread is using the same connection.

  • Many threads can access different result sets that are retrieved with .

  • If you use , you have to ensure that no other thread is using the same connection until the result set is closed. However, it really is best for threaded clients that share the same connection to use .

  • If you want to use multiple threads on the same connection, you must have a mutex lock around your and call combination. Once is ready, the lock can be released and other threads may query the same connection.

  • If you program with POSIX threads, you can use and to establish and release a mutex lock.

You need to know the following if you have a thread that is calling MySQL functions which did not create the connection to the MySQL database:

When you call or , MySQL creates a thread-specific variable for the thread that is used by the debug library (among other things).

If you call a MySQL function, before the thread has called or , the thread does not have the necessary thread-specific variables in place and you are likely to end up with a core dump sooner or later.

The get things to work smoothly you have to do the following:

  1. Call at the start of your program if it calls any other MySQL function before calling .

  2. Call in the thread handler before calling any MySQL function.

  3. In the thread, call before calling . This frees the memory used by MySQL thread-specific variables.

You may get some errors because of undefined symbols when linking your client with . In most cases this is because you haven't included the thread libraries on the link/compile line.

24.3.16. libmysqld, la biblioteca del servidor MySQL incrustado (embedded)

24.3.16.1. Panorámica de la librería del servidor MySQL incrustado (embedded)

The embedded MySQL server library makes it possible to run a full-featured MySQL server inside a client application. The main benefits are increased speed and more simple management for embedded applications.

The embedded server library is based on the client/server version of MySQL, which is written in C/C++. Consequently, the embedded server also is written in C/C++. There is no embedded server available in other languages.

The API is identical for the embedded MySQL version and the client/server version. To change an old threaded application to use the embedded library, you normally only have to add calls to the following functions:

Function When to Call
Should be called before any other MySQL function is called, preferably early in the function.
Should be called before your program exits.
Should be called in each thread you create that accesses MySQL.
Should be called before calling

Then you must link your code with instead of .

The () functions are also included in to allow you to change between the embedded and the client/server version by just linking your application with the right library. See Sección 24.3.12.1, “.

24.3.16.2. Compilar programas con

To get a library you should configure MySQL with the option. See Sección 2.8.2, “Opciones típicas de configure.

When you link your program with , you must also include the system-specific libraries and some libraries that the MySQL server uses. You can get the full list of libraries by executing mysql_config --libmysqld-libs.

The correct flags for compiling and linking a threaded program must be used, even if you do not directly call any thread functions in your code.

To compile a C program to include the necessary files to embed the MySQL server library into a compiled version of a program, use the GNU C compiler (). The compiler will need to know where to find various files and need instructions on how to compile the program. Below is an example of how a program could be compiled from the command-line:

gcc mysql_test.c -o mysql_test -lz \
`/usr/local/mysql/bin/mysql_config --include --libmysqld-libs`

Immediately following the command is the name of the uncompiled C program file. After it, the option is given to indicate that the file name that follows is the name that the compiler is to give to the output file, the compiled program. The next line of code tells the compiler to obtain the location of the include files and libraries and other settings for the system on which it's compiled. Because of a problem with mysql_config, the option (for compression) is added here. The mysql_config piece is contained in backticks, not single quotes.

24.3.16.3. Restricciones cuando se utiliza el servidor MySQL incrustado (embedded)

The embedded server has the following limitations:

  • No support for tables. (This is mainly done to make the library smaller)

  • No user-defined functions (UDFs).

  • No stack trace on core dump.

  • No internal RAID support. (This is not normally needed as most current operating systems support big files).

  • You cannot set this up as a master or a slave (no replication).

  • You cannot connect to an embedded server from an outside process with sockets or TCP/IP. However, you can connect to an intermediate application, which in turn can connect to an embedded server on the behalf of a remote client or outside process.

Some of these limitations can be changed by editing the include file and recompiling MySQL.

24.3.16.4. Opciones con el servidor incrustado (embedded)

Any options that may be given with the mysqld server daemon, may be used with an embedded server library. Server options may be given in an array as an argument to the , which initializes the server. They also may be given in an option file like . To specify an option file for a C program, use the option as one of the elements of the second argument of the function. See Sección 24.3.12.1, “ for more information on the function.

Using option files can make it easier to switch between a client/server application and one where MySQL is embedded. Put common options under the group. These are read by both MySQL versions. Client/server-specific options should go under the section. Put options specific to the embedded MySQL server library in the section. Options specific to applications go under section labeled . See Sección 4.3.2, “Usar ficheros de opciones”.

24.3.16.5. Cosas por hacer (TODO) en el servidor incrustado (embedded)

  • We are going to provide options to leave out some parts of MySQL to make the library smaller.

  • There is still a lot of speed optimization to do.

  • Errors are written to . We will add an option to specify a filename for these.

  • We have to change InnoDB not to be so verbose when using the embedded version. If your database does not contain InnoDB tables, to suppress related messages you can add the option to the options file under the group , or when initializing the server with mysql_server_init().

24.3.16.6. Ejemplos de servidor incrustado (embedded)

These two example programs should work without any changes on a Linux or FreeBSD system. For other operating systems, minor changes are needed, mostly with file paths. These examples are designed to give enough details for you to understand the problem, without the clutter that is a necessary part of a real application. The first example is very straightforward. The second example is a little more advanced with some error checking. The first is followed by a command-line entry for compiling the program. The second is followed by a GNUmake file that may be used for compiling instead.

Example 1

#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include "mysql.h"

MYSQL *mysql;
MYSQL_RES *results;
MYSQL_ROW record;

static char *server_options[] = { "mysql_test", "--defaults-file=my.cnf" };
int num_elements = sizeof(server_options)/ sizeof(char *);

static char *server_groups[] = { "libmysqld_server", "libmysqld_client" };

int main(void)
{
   mysql_server_init(num_elements, server_options, server_groups);
   mysql = mysql_init(NULL);
   mysql_options(mysql, MYSQL_READ_DEFAULT_GROUP, "libmysqld_client");
   mysql_options(mysql, MYSQL_OPT_USE_EMBEDDED_CONNECTION, NULL);

   mysql_real_connect(mysql, NULL,NULL,NULL, "database1", 0,NULL,0);

   mysql_query(mysql, "SELECT column1, column2 FROM table1");

   results = mysql_store_result(mysql);

   while((record = mysql_fetch_row(results))) {
      printf("%s - %s \n", record[0], record[1]);
   }

   mysql_free_result(results);
   mysql_close(mysql);
   mysql_server_end();

   return 0;
}

Here is the command line for compiling the above program:

gcc test1_libmysqld.c -o test1_libmysqld -lz \
 `/usr/local/mysql/bin/mysql_config --include --libmysqld-libs`

Example 2

To try out the example, create an directory at the same level as the mysql-4.0 source directory. Save the source and the in the directory, and run GNU from inside the directory.

/*
 * A simple example client, using the embedded MySQL server library
*/

#include <mysql.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>

MYSQL *db_connect(const char *dbname);
void db_disconnect(MYSQL *db);
void db_do_query(MYSQL *db, const char *query);

const char *server_groups[] = {
  "test2_libmysqld_SERVER", "embedded", "server", NULL
};

int
main(int argc, char **argv)
{
  MYSQL *one, *two;

  /* mysql_server_init() must be called before any other mysql
   * functions.
   *
   * You can use mysql_server_init(0, NULL, NULL), and it
   * initializes the server using groups = {
   *   "server", "embedded", NULL
   *  }.
   *
   * In your $HOME/.my.cnf file, you probably want to put:

[test2_libmysqld_SERVER]
language = /path/to/source/of/mysql/sql/share/english

   * You could, of course, modify argc and argv before passing
   * them to this function.  Or you could create new ones in any
   * way you like.  But all of the arguments in argv (except for
   * argv[0], which is the program name) should be valid options
   * for the MySQL server.
   *
   * If you link this client against the normal mysqlclient
   * library, this function is just a stub that does nothing.
   */
  mysql_server_init(argc, argv, (char **)server_groups);

  one = db_connect("test");
  two = db_connect(NULL);

  db_do_query(one, "SHOW TABLE STATUS");
  db_do_query(two, "SHOW DATABASES");

  mysql_close(two);
  mysql_close(one);

  /* This must be called after all other mysql functions */
  mysql_server_end();

  exit(EXIT_SUCCESS);
}

static void
die(MYSQL *db, char *fmt, ...)
{
  va_list ap;
  va_start(ap, fmt);
  vfprintf(stderr, fmt, ap);
  va_end(ap);
  (void)putc('\n', stderr);
  if (db)
    db_disconnect(db);
  exit(EXIT_FAILURE);
}

MYSQL *
db_connect(const char *dbname)
{
  MYSQL *db = mysql_init(NULL);
  if (!db)
    die(db, "mysql_init failed: no memory");
  /*
   * Notice that the client and server use separate group names.
   * This is critical, because the server does not accept the
   * client's options, and vice versa.
   */
  mysql_options(db, MYSQL_READ_DEFAULT_GROUP, "test2_libmysqld_CLIENT");
  if (!mysql_real_connect(db, NULL, NULL, NULL, dbname, 0, NULL, 0))
    die(db, "mysql_real_connect failed: %s", mysql_error(db));

  return db;
}

void
db_disconnect(MYSQL *db)
{
  mysql_close(db);
}

void
db_do_query(MYSQL *db, const char *query)
{
  if (mysql_query(db, query) != 0)
    goto err;

  if (mysql_field_count(db) > 0)
  {
    MYSQL_RES   *res;
    MYSQL_ROW    row, end_row;
    int num_fields;

    if (!(res = mysql_store_result(db)))
      goto err;
    num_fields = mysql_num_fields(res);
    while ((row = mysql_fetch_row(res)))
    {
      (void)fputs(">> ", stdout);
      for (end_row = row + num_fields; row < end_row; ++row)
        (void)printf("%s\t", row ? (char*)*row : "NULL");
      (void)fputc('\n', stdout);
    }
    (void)fputc('\n', stdout);
    mysql_free_result(res);
  }
  else
    (void)printf("Affected rows: %lld\n", mysql_affected_rows(db));

  return;

err:
  die(db, "db_do_query failed: %s [%s]", mysql_error(db), query);
}

# This assumes the MySQL software is installed in /usr/local/mysql
inc      := /usr/local/mysql/include/mysql
lib      := /usr/local/mysql/lib

# If you have not installed the MySQL software yet, try this instead
#inc      := $(HOME)/mysql-4.0/include
#lib      := $(HOME)/mysql-4.0/libmysqld

CC       := gcc
CPPFLAGS := -I$(inc) -D_THREAD_SAFE -D_REENTRANT
CFLAGS   := -g -W -Wall
LDFLAGS  := -static
# You can change -lmysqld to -lmysqlclient to use the
# client/server library
LDLIBS    = -L$(lib) -lmysqld -lz -lm -lcrypt

ifneq (,$(shell grep FreeBSD /COPYRIGHT 2>/dev/null))
# FreeBSD
LDFLAGS += -pthread
else
# Assume Linux
LDLIBS += -lpthread
endif

# This works for simple one-file test programs
sources := $(wildcard *.c)
objects := $(patsubst %c,%o,$(sources))
targets := $(basename $(sources))

all: $(targets)

clean:
        rm -f $(targets) $(objects) *.core

24.3.16.7. Licenciamiento del servidor incrustado (embedded)

We encourage everyone to promote free software by releasing code under the GPL or a compatible license. For those who are not able to do this, another option is to purchase a commercial license for the MySQL code from MySQL AB. For details, please see http://www.mysql.com/company/legal/licensing/.