pike.git / lib / modules / __builtin.pmod / Sql.pmod / Connection.pike

version» Context lines:

pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:362:   //! @[set_charset] will throw an error).   //!   //! @seealso   //! @[set_charset], @[Sql.mysql.get_charset]   {    return UNDEFINED;   }      // FIXME: _sprintf().    - protected array(mapping(string:mixed)) res_obj_to_array(.Result res_obj) + array(mapping(string:mixed)) +  res_obj_to_array(array(mixed)|.Result res_obj, void|array(mapping) fields)   {    if (!res_obj)    return 0;       array(mapping(string:mixed)) res = ({});    while (res_obj)    {    // Not very efficient, but sufficient    array(string) fieldnames; -  +  array(array(mixed)) rows;    array(mixed) row; -  +  int i;    -  array(mapping) fields = res_obj->fetch_fields(); -  if(!sizeof(fields)) return ({}); +  if (!fields) +  fields = res_obj->fetch_fields(); +  if(!sizeof(fields)) return res;       int has_table = fields[0]->table && fields[0]->table!="";       if(has_table)    fieldnames = (map(fields,    lambda (mapping(string:mixed) m) {    return (m->table||"") + "." + m->name;    }) +    fields->name);    else    fieldnames = fields->name;       if (case_convert)    fieldnames = map(fieldnames, lower_case);    -  +  if (arrayp(res_obj)) +  rows = res_obj; +  else { +  fields = 0; +  rows = ({}); +  while (row = res_obj->fetch_row_array()) +  rows += row; +  } +     if(has_table) -  while (row = res_obj->fetch_row()) -  res += ({ mkmapping(fieldnames, row + row) }); +  foreach (rows; i; row) +  rows[i] = mkmapping(fieldnames, row + row);    else -  while (row = res_obj->fetch_row()) -  res += ({ mkmapping(fieldnames, row) }); +  foreach (rows; i; row) +  rows[i] = mkmapping(fieldnames, row);    -  +  res += rows;    // Try the next result. -  res_obj = res_obj->next_result && res_obj->next_result(); +  res_obj = objectp(res_obj) +  && res_obj->next_result && res_obj->next_result();    }    return res;   }      //! The textual description of the last   //! server-related error. Returns @expr{0@} if no error has occurred   //! yet. It is not cleared upon reading (can be invoked multiple   //! times, will return the same result until a new error occurs).   //!   //! @note
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:543:   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results in untyped mode.   //!   //! @param q   //! Query to send to the SQL-server. This can either be a string with the   //! query, or a previously compiled query (see @[compile_query()]).   //!   //! @returns - //! The result is returned as an @[Sql.sql_result] object in untyped + //! The result is returned as an @[Sql.Result] object in untyped   //! mode. This allows for having some more info about the result as   //! well as processing the result in a streaming fashion, although the   //! result itself wasn't obtained streamingly from the server.   //!   //! Returns @expr{0@} if the query didn't return any result   //! (e.g. @tt{INSERT@} or similar).   //!   //! @throws   //! Throws an exception if the query fails.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:591:   //! the variable is used.   //!   //! @code   //! res = query("SELECT foo FROM bar WHERE gazonk=:baz",   //! ([":baz":"value"]));   //! @endcode   //!   //! Binary values (BLOBs) may need to be placed in multisets.   //!   //! @returns - //! The result is returned as an @[Sql.sql_result] object in untyped + //! The result is returned as an @[Sql.Result] object in untyped   //! mode. This allows for having some more info about the result as   //! well as processing the result in a streaming fashion, although the   //! result itself wasn't obtained streamingly from the server.   //!   //! Returns @expr{0@} if the query didn't return any result   //! (e.g. @tt{INSERT@} or similar).   //!   //! @throws   //! Throws an exception if the query fails.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:637:   //!   //! @param extraarg   //! @param extraargs   //! Arguments as you would use in sprintf. They are automatically   //! quoted.   //!   //! @code   //! res = query("select foo from bar where gazonk=%s","value");   //! @endcode   //! - //! The result is returned as an @[Sql.sql_result] object in untyped + //! The result is returned as an @[Sql.Result] object in untyped   //! mode. This allows for having some more info about the result as   //! well as processing the result in a streaming fashion, although the   //! result itself wasn't obtained streamingly from the server. Returns   //! @expr{0@} if the query didn't return any result (e.g. @tt{INSERT@}   //! or similar).   //!   //! The default implementation normalizes @[q] and @[extraargs] to   //! use the bindings mapping (via @[handle_extraargs()]), and calls   //! one of the other variants of @[big_query()] with the result.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:699:    mixed ... extraargs)   {    return res_obj_to_array(big_query(q, @extraargs));   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results in typed mode.   //!   //! For the argument, please see the @[big_query()] function.   //! - //! The result is returned as an @[Sql.sql_result] object in typed + //! The result is returned as an @[Sql.Result] object in typed   //! mode. This allows for having some more info about the result as   //! well as processing the result in a streaming fashion, although the   //! result itself wasn't obtained streamingly from the server. Returns   //! @expr{0@} if the query didn't return any result (e.g. @tt{INSERT@}   //! or similar).   //!   //! @note   //! Typed mode is not supported by all sql databases. If not   //! supported, an error is thrown.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:728:   //!   //! @seealso   //! @[query], @[typed_query], @[big_query], @[streaming_query]   int|.Result big_typed_query(object|string q);      //! Send an SQL query synchronously to the SQL-server and return   //! the results in typed mode.   //!   //! For the arguments, please see the @[big_query()] function.   //! - //! The result is returned as an @[Sql.sql_result] object in typed + //! The result is returned as an @[Sql.Result] object in typed   //! mode. This allows for having some more info about the result as   //! well as processing the result in a streaming fashion, although the   //! result itself wasn't obtained streamingly from the server. Returns   //! @expr{0@} if the query didn't return any result (e.g. @tt{INSERT@}   //! or similar).   //!   //! @note   //! Typed mode is not supported by all sql databases. If not   //! supported, an error is thrown.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:759:    mapping(string|int:mixed) bindings)   {    return big_typed_query(emulate_bindings(q, bindings));   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results in typed mode.   //!   //! For the arguments, please see the @[big_query()] function.   //! - //! The result is returned as an @[Sql.sql_result] object in typed + //! The result is returned as an @[Sql.Result] object in typed   //! mode. This allows for having some more info about the result as   //! well as processing the result in a streaming fashion, although the   //! result itself wasn't obtained streamingly from the server. Returns   //! @expr{0@} if the query didn't return any result (e.g. @tt{INSERT@}   //! or similar).   //!   //! @note   //! Typed mode is not supported by all sql databases. If not   //! supported, an error is thrown.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:822:   array(mapping(string:mixed)) typed_query(object|string q, mixed ... extraargs)   {    return res_obj_to_array(big_typed_query(q, @extraargs));   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results streaming in untyped mode.   //!   //! For the arguments, please see the @[low_big_query()] function.   //! - //! The result is returned as a streaming @[Sql.sql_result] object in + //! The result is returned as a streaming @[Sql.Result] object in   //! untyped mode. This allows for having results larger than the   //! available memory, and returning some more info about the result.   //! Returns @expr{0@} if the query didn't return any result (e.g.   //! INSERT or similar). For the other arguments, they are the same as   //! for the @[query()] function.   //!   //! Called by @[streaming_query()] after it has processed any bindings.   //!   //! This variant function is intended for overriding by drivers.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:849:   int|.Result streaming_query(object|string q)   {    return big_query(q);   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results streaming in untyped mode.   //!   //! For the arguments, please see the @[low_big_query()] function.   //! - //! The result is returned as a streaming @[Sql.sql_result] object in + //! The result is returned as a streaming @[Sql.Result] object in   //! untyped mode. This allows for having results larger than the   //! available memory, and returning some more info about the result.   //! Returns @expr{0@} if the query didn't return any result (e.g.   //! INSERT or similar). For the other arguments, they are the same as   //! for the @[query()] function.   //!   //! Called by @[streaming_query()] after it has processed any bindings.   //!   //! This variant function is intended for overriding by drivers that   //! actually implement bindings.
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:878:    mapping(string:mixed) bindings)   {    return streaming_query(emulate_bindings(q, bindings));   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results streaming in untyped mode.   //!   //! For the arguments, please see the @[query()] function.   //! - //! The result is returned as a streaming @[Sql.sql_result] object in + //! The result is returned as a streaming @[Sql.Result] object in   //! untyped mode. This allows for having results larger than the   //! available memory, and returning some more info about the result.   //! Returns @expr{0@} if the query didn't return any result (e.g.   //! INSERT or similar). For the other arguments, they are the same as   //! for the @[query()] function.   //!   //! @note   //! Streaming operation is not supported by all sql databases.   //! If not supported, this function will fall back to calling   //! @[big_query()].
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:904:    string|multiset|int|float|object ... extraargs)   {    return streaming_query(@handle_extraargs(q, ({ extraarg }) + extraargs));   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results streaming in typed mode.   //!   //! For the arguments, please see the @[query()] function.   //! - //! The result is returned as a streaming @[Sql.sql_result] object in + //! The result is returned as a streaming @[Sql.Result] object in   //! typed mode. This allows for having results larger than the   //! available memory, and returning some more info about the result.   //! Returns @expr{0@} if the query didn't return any result (e.g.   //! INSERT or similar).   //!   //!   //! Called by @[streaming_query()] after it has processed any bindings.   //!   //! This function is intended for overriding by drivers.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:932:   int|.Result streaming_typed_query(object|string q)   {    return big_typed_query(q);   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results streaming in typed mode.   //!   //! For the arguments, please see the @[query()] function.   //! - //! The result is returned as a streaming @[Sql.sql_result] object in + //! The result is returned as a streaming @[Sql.Result] object in   //! typed mode. This allows for having results larger than the   //! available memory, and returning some more info about the result.   //! Returns @expr{0@} if the query didn't return any result (e.g.   //! INSERT or similar).   //!   //!   //! Called by @[streaming_query()] after it has processed any bindings.   //!   //! This function is intended for overriding by drivers.   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:961:    mapping(string|int:mixed) bindings)   {    return streaming_typed_query(emulate_bindings(q, bindings));   }      //! Send an SQL query synchronously to the SQL-server and return   //! the results streaming in typed mode.   //!   //! For the arguments, please see the @[query()] function.   //! - //! The result is returned as a streaming @[Sql.sql_result] object in + //! The result is returned as a streaming @[Sql.Result] object in   //! typed mode. This allows for having results larger than the   //! available memory, and returning some more info about the result.   //! Returns @expr{0@} if the query didn't return any result (e.g.   //! INSERT or similar).   //!   //! @note   //! Neither streaming operation nor typed results are supported   //! by all sql databases. If not supported, this function will   //! fall back to calling @[big_typed_query()].   //!
pike.git/lib/modules/__builtin.pmod/Sql.pmod/Connection.pike:1201:       if (res && wild) {    res =    filter(res,    map(res->name,    Regexp(replace(wild, ({"%", "_"}), ({".*", "."})))->match));    }       return res;   } +  + //! Sends a query to the database asynchronously, discards all query result + //! records. + //! + //! @returns + //! A @[Concurrent.Future] object which on failure/success passes + //! a @[Sql.FutureResult] object to evaluate the query. + //! + //! @seealso + //! @[promise_query()], @[promise_query_first_result()], + //! @[promise_query_result()], @[big_typed_query()] + public Concurrent.Future promise_query_discard(string q, +  void|mapping(string|int:mixed) bindings) { +  Concurrent.Promise p = Concurrent.Promise(); +  .FutureResult(this, p, q, bindings, 0); +  return p->future(); + } +  + //! Sends a query to the database asynchronously, expects at least + //! a single record from the database; will discard any further + //! records. + //! + //! @returns + //! A @[Concurrent.Future] object which on failure/success passes + //! a @[Sql.FutureResult] object to evaluate the query. + //! + //! @seealso + //! @[promise_query()], @[promise_query_result()], + //! @[promise_query_discard()], @[big_typed_query()] + public Concurrent.Future promise_query_first_result(string q, +  void|mapping(string|int:mixed) bindings) { +  Concurrent.Promise p = Concurrent.Promise(); +  .FutureResult(this, p, q, bindings, 1); +  return p->future(); + } +  + //! Sends a query to the database asynchronously, expects at least + //! a single record from the database. + //! + //! @returns + //! A @[Concurrent.Future] object which on failure/success passes + //! a @[Sql.FutureResult] object to evaluate the query. + //! + //! @seealso + //! @[promise_query()], @[promise_query_first_result()], + //! @[promise_query_discard()], @[big_typed_query()] + public Concurrent.Future promise_query_result(string q, +  void|mapping(string|int:mixed) bindings) { +  Concurrent.Promise p = Concurrent.Promise(); +  .FutureResult(this, p, q, bindings, 2); +  return p->future(); + } +  + //! Sends a query to the database asynchronously. + //! + //! @returns + //! A @[Concurrent.Future] object which on failure/success passes + //! a @[Sql.FutureResult] object to evaluate the query. + //! + //! @seealso + //! @[promise_query_first_result()], @[promise_query_result()], + //! @[promise_query_discard()], @[big_typed_query()] + //! + //! @example + //! @code + //! + //! Sql.Connection db = Sql.Connection("..."); + //! Concurrent.Future q1 = db->promise_query("SELECT :bar::INT", (["bar":1])); + //! Concurrent.Future q2 = db->promise_query("SELECT :foo::INT", (["foo":2])); + //! + //! array(Concurrent.Future) all = ({ q1, q2 }); + //! + //! /* + //! To get a callback for each of the requests + //! */ + //! + //! all->on_success(lambda (Sql.FutureResult resp) { + //! werror("Got result %O from %O\n", resp->data, resp->query); + //! }); + //! all->on_failure(lambda (Sql.FutureResult resp) { + //! werror("Request %O failed: %O\n", resp->query, resp->exception); + //! }); + //! + //! /* + //! To get a callback when all of the requests are done. In this case + //! on_failure will be called if any of the request fails. + //! */ + //! + //! Concurrent.Future all2 = Concurrent.results(all); + //! + //! all2->on_success(lambda (array(Sql.FutureResult) resp) { + //! werror("All requests were successful: %O\n", resp); + //! }); + //! all->on_failure(lambda (Sql.FutureResult resp) { + //! werror("Requests %O failed with %O.\n", resp->query, resp->exception); + //! }); + //! @endcode + public Concurrent.Future promise_query(string q, +  void|mapping(string|int:mixed) bindings) { +  Concurrent.Promise p = Concurrent.Promise(); +  .FutureResult(this, p, q, bindings, 3); +  return p->future(); + }