Send a text or image value to the server.
RETCODE dbwritetext(dbproc, objname, textptr, textptrlen, timestamp, log, size, text) DBPROCESS *dbproc; char *objname; DBBINARY *textptr; DBTINYINT textptrlen; DBBINARY *timestamp; DBBOOL log; DBINT size; BYTE *text;
A pointer to the DBPROCESS structure that provides the connection for a particular front-end/server process. It contains all the information that DB-Library uses to manage communications and data between the front end and server.
The database table and column name that is separated by a period.
A pointer to the text pointer of the text or image value to be modified. This can be obtained by calling dbtxptr. The text pointer must be a valid one, as described on the dbtxptr reference page.
This parameter is included for future compatibility. For now, its value must be the defined constant DBTXPLEN.
A pointer to the text timestamp of the text or image value to be modified. This can be obtained using dbtxtimestamp or dbtxtsnewval. This value changes whenever the text or image value itself is changed. This parameter is optional and may be passed as NULL.
A boolean value specifying whether this dbwritetext operation should be recorded in the transaction log.
The total size, in bytes, of the text or image value to be written. Since dbwritetext uses this parameter as its only guide to determining how many bytes to send, size must not exceed the actual size of the value.
The address of a buffer containing the text or image value to be written. If this pointer is NULL, the application must subsequently call dbmoretext one or more times, until all size bytes of data have been sent to the server.
SUCCEED or FAIL.
A common cause for failure is an invalid timestamp parameter. This occurs if, between the time the application retrieves the text column and the time the application calls dbwritetext to update it, a second application intervenes with its own update.
dbwritetext updates SYBTEXT and SYBIMAGE values. It allows the application to send long values to the server without having to copy them into a Transact-SQL update statement. In addition, dbwritetext gives applications access to the text timestamp mechanism, which can be used to ensure that two competing application users do not inadvertently wipe out each other’s modifications to the same value in the database.
The timestamp parameter is optional.
If the timestamp parameter is supplied, dbwritetext succeeds only if the value of the timestamp parameter matches the text column’s timestamp in the database. If a match occurs, dbwritetext updates the text column and at the same time updates the column’s timestamp with the current time. This has the effect of governing updates by competing applications—an application’s dbwritetext call fails if a second application updated the text column between the time the first application retrieved the column and the time it made its dbwritetext call.
If the timestamp parameter is not supplied, dbwritetext updates the text column regardless of the value of the column’s timestamp.
The value to use as the timestamp parameter is placed in an application’s DBPROCESS when the application performs a select on a text or image value. It can be retrieved from the DBPROCESS using dbtxtimestamp.
In addition, after each successful dbwritetext operation, which may include a number of calls to dbmoretext, Adaptive Server Enterprise sends a new text timestamp value back to DB-Library. dbtxtsnewval provides a way for an application to retrieve this new value.
dbwritetext is similar in function to the Transact-SQL writetext command. It is usually more efficient to call dbwritetext than to send a writetext command through the command buffer. In addition, dbwritetext can handle columns up to 2GB in length, while writetext data is limited to approximately 120K. See the Adaptive Server Enterprise Reference Manual.
dbwritetext can be invoked with or without logging, according to the value of the log parameter.
While logging aids media recovery, logging text data quickly increases the size of the transaction log. If you are logging dbwritetext operations, make sure that the transaction log resides on a separate database device. For details, see the Adaptive Server Enterprise System Administration Guide, the create database reference page, and the sp_logdevice reference page in the Adaptive Server Enterprise Reference Manual for details.
To use dbwritetext with logging turned off, the database option select into/bulkcopy must be set to “true”. The following SQL command will do this:
sp_dboption ’mydb’, ’select into/bulkcopy’, ’true’
See the Adaptive Server Enterprise Reference Manual for further details on sp_dboption.
The application can send a text or image value to the server all at once or a chunk at a time. dbwritetext by itself handles sending an entire text or image value. The use of dbwritetext with dbmoretext allows the application to send a large text or image value to the server in the form of a number of smaller chunks. This is particularly useful with operating systems unable to allocate extremely long data buffers.
Sending an entire text or image value requires a non-NULL text parameter. Then, dbwritetext will execute the data transfer from start to finish, including any necessary calls to dbsqlok and dbresults. Here is a code fragment that illustrates this use of dbwritetext:
LOGINREC *login;
DBPROCESS *q_dbproc;
DBPROCESS *u_dbproc;
DBCHAR abstract_var[512];
/* Initialize DB-Library. */
if (dbinit() == FAIL)
exit(ERREXIT);
/*
** Open separate DBPROCESSes for querying and updating.
** This is not strictly necessary in this example,
** which retrieves only one row. However, this
** approach becomes essential when performing updates
** on multiple rows of retrieved data.
*/
login = dblogin();
q_dbproc = dbopen(login, NULL);
u_dbproc = dbopen(login, NULL);
/* The database column "abstract" is a text column.
** Retrieve the value of one of its rows.
*/
dbcmd(q_dbproc, "select abstract from articles where \
article_id = 10");
dbsqlexec(q_dbproc);
dbresults(q_dbproc);
dbbind(q_dbproc, 1, STRINGBIND, (DBINT) 0,
abstract_var);
/*
** For simplicity, we’ll assume that just one row is
** returned.
*/
dbnextrow(q_dbproc);
/* Here we can change the value of "abstract_var" */
/* For instance ... */
strcpy(abstract_var, "A brand new value.");
/* Update the text column */
dbwritetext (u_dbproc, "articles.abstract",
dbtxptr(q_dbproc, 1), DBTXPLEN,
dbtxtimestamp(q_dbproc, 1), TRUE,
(DBINT)strlen(abstract_var), abstract_var);
/* We’re all done */
dbexit();
To send chunks of text or image, rather than the whole value at once, set the text parameter to NULL. Then, dbwritetext will return control to the application immediately after notifying the server that a text transfer is about to begin. The actual text will be sent to the server with dbmoretext, which can be called multiple times, once for each chunk. Here is a code fragment that illustrates the use of dbwritetext with dbmoretext:
LOGINREC *login;
DBPROCESS *q_dbproc;
DBPROCESS *u_dbproc;
DBCHAR part1[512];
static DBCHAR part2[512] = " This adds another \
sentence to the text.";
if (dbinit() == FAIL)
exit(ERREXIT);
login = dblogin();
q_dbproc = dbopen(login, NULL);
u_dbproc = dbopen(login, NULL);
dbcmd(q_dbproc, "select abstract from articles where \
article_id = 10");
dbsqlexec(q_dbproc);
dbresults(q_dbproc);
dbbind(q_dbproc, 1, STRINGBIND, (DBINT) 0, part1);
/*
** For simplicity, we’ll assume that just one row is
** returned.
*/
dbnextrow(q_dbproc);
/*
** Here we can change the value of part of the text
** column. In this example, we will merely add a
** sentence to the end of the existing text.
*/
/* Update the text column */
dbwritetext (u_dbproc, "articles.abstract",
dbtxptr(q_dbproc, 1), DBTXPLEN,
dbtxtimestamp(q_dbproc, 1), TRUE,
(DBINT)(strlen(part1) + strlen(part2)), NULL);
dbsqlok(u_dbproc);
dbresults(u_dbproc);
/* Send the update value in chunks */
dbmoretext(u_dbproc, (DBINT)strlen(part1), part1);
dbmoretext(u_dbproc, (DBINT)strlen(part2), part2);
dbsqlok(u_dbproc);
dbresults(u_dbproc);
dbexit();
Note the required calls to dbsqlok and dbresults between the call to dbwritetext and the first call to dbmoretext, and after the final call to dbmoretext.
When dbwritetext is used with dbmoretext, it locks the specified database text column. The lock is not released until the final dbmoretext has sent its data. This ensures that a second application does not read or update the text column in the midst of the first application’s update.
You cannot use dbwritetext on text or image columns in views.
The DB-Library/C option DBTEXTSIZE affects the value of the server @@textsize global variable, which restricts the size of text or image values that Adaptive Server Enterprise returns. @@textsize has a default value of 32,768 bytes. An application that retrieves text or image values larger than 32,768 bytes will need to call dbsetopt to make @@textsize larger.
The DB-Library/C option DBTEXTLIMIT limits the size of text or image values that DB-Library/C will read.