4

I'm new to using the gwan server(link) and for that matter programming in c. I wanted to know what was the easiest way to use mysql in a c script for the gwan server?

I've experimented with dbi.c as used here and the project page can be found here, but also found that there is a c API for mysql itself which you can find here.

Anyone have experience using either or both? What are some of the pros/cons? Are there other libraries that make connecting to mysql easy for a noob like myself?

Any help appreciated.

Thanks!

[EDIT] Also is libdbi thread safe? it appears to not be.

[EDIT 2] It appears that the mysql lib itself is the easy way to go unless you think might be switching database types later as libdbi appears to be able to have different drivers which is nice for abstraction.

Relating to GWAN for me if i had any "mysql code" in the main function of a handler it appeared to be unsafe and caused random errors intermittently, but if i put the "mysql code" in the init function and put any data i need in a kv store accessed off of one of the global pointers the random errors went away completely. (I was using libdbi i assume it would be the same for the mysql api)

Hope this helps

sbditto85
  • 1,485
  • 14
  • 21

1 Answers1

4

I always prefer using the native c api...

#pragma link "/usr/lib/libmysqlclient.so"

#include "gwan.h"
#include <mysql/mysql.h>


int
main (int argc, char **argv)
{
  MYSQL_RES *result;
  MYSQL_ROW row;
  MYSQL conn, *conn_h;

  conn_h = mysql_init (&conn);
  if (!conn_h)
    {
      return 200;
    }

  if (!mysql_real_connect (conn_h, "localhost", ctx->usr, ctx->psw, NULL, 0, NULL, 0))
    {
      mysql_close (conn_h);
      return 200;
    }

  mysql_select_db (conn_h, "");

  char *query = "";

  if (mysql_query (conn_h, query))
    {
      mysql_close (conn_h);
      return 200;
    }

  result = mysql_store_result (conn_h);
  if (!result)
    {
      mysql_close (conn_h);
      return 200;
    }

  if (mysql_num_rows (result) == 0)
    {
      return 200;
    }

  while ((row = mysql_fetch_row (result)))
    {
      /* do something with row[i] */
    }

  mysql_free_result (result);
  mysql_close (conn_h);

  return 200;  // Ok
}

Keep in mind you need to initialize the mysql library if you plan to spawn threads (this code is not thread safe).

Hope this help you someway.

  • so is their a thread safe way of connecting? i was under the impression that gwan uses threads to do many connections concurrently. – sbditto85 Jul 09 '12 at 14:31
  • @sbditto85 The connection is always thread safe. You need to take care only if you spawn threads inside your connection, what I saw of little use up to now. – Josuel Guimaraes Jul 10 '12 at 12:43
  • but dont you have to use the thread safe lib? `The thread-safe client library, libmysqlclient_r, is thread-safe per connection. ` [see mysql "how to write a threaded client"](http://dev.mysql.com/doc/refman/5.0/en/threaded-clients.html) or am i misunderstanding things? again sorry I'm still a noob with c programming. – sbditto85 Jul 10 '12 at 13:32
  • more specifically i thought that if we use anything in gwan it must be thread safe, is that true? – sbditto85 Jul 10 '12 at 13:39
  • 1
    @sbditto85 gwan uses threads to process incoming connections. The way it does it doesn't matter for your c script (servlet), your connetion is always thread-safe regarding the server. If you spawn threads inside your script, you should take care of two or more threds accessing the connection at the same time, as you whould with any other resource. Only in certain circumstantes (it depends on your script) you must use libmysqlclient_r. Anyway, you must always initialize the mysql library (mysql_library_init()) when working with more than one thread in your script. – Josuel Guimaraes Jul 10 '12 at 20:13
  • 1
    @sbditto85 Just to clarify: we have two kinds of connections, one between gwan and the mysql server and another between the browser and gwan. The latter gwan takes care of. The first one we must take care of ourselves (with appropriate mysql code). – Josuel Guimaraes Jul 10 '12 at 20:37
  • Thanks that clarified it up for me :) – sbditto85 Jul 11 '12 at 15:34
  • Also it appears that if you use any mysql connection in a handler it needs to be done in a thread safe way (It seems i was running into a few race conditions) so I just used the database when the handler was initializing and put the data in a kv store which appears to be atomic or at least the race conditions stopped. – sbditto85 Jul 11 '12 at 15:39
  • sbditto85 I've had the same problem until I realized every incoming connection passes through the handler (so you must use mysql in a safe way). And yes, kv store is thread safe (lock-free, wait-free). – Josuel Guimaraes Jul 12 '12 at 18:27