odbc.e v1.34
Matt Lewis
matthewwalkerlewis@gmail.com
ODBC.e is a library that opens up Open Database Connectivity (ODBC) to Euphoria. At this point, virtually every database has an ODBC driver, which allows other applications to interact with the database through the standard ODBC API, and using Structured Query Language (SQL).
For more details on ODBC, I recommend looking at Microsoft's ODBC API Reference.
In order to use this library, you'll either need to set up a User Data Source Name (DSN) (System DSN's should work, too, but I haven't tested them yet) or use a connection string to connect to a database. See your database manual, or Windows/UnixODBC help for info on setting up a DSN.
Once the DSN is up and running, you're ready to use the database with Euphoria!
LICENSE AND DISCLAIMER
This software is freeware, but you must give me credit for any applications developed with it. You can modify any of the code, so long as you do not take credit for any of the original source, and any modifications must be marked as such.
THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFIT; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
Included files: * odbc.e : ODBC Library * wxOdbc.exw : Win32/Linux Demo * print.e : Used by the demoNot included: * wxEuphoria v0.4.0 : Required for the demo
Topic | Description |
Index | Alphabetical list of all items. |
API | How to use this library |
Change Log | History of ODBC.e |
Credits | Who helped me out (whether they know it or not) |
Cursors | Scrolling through Data Sets |
Data types | Working with different data types |
Way Ahead | What's next for odbc.ew |
Before you do anything, make sure you call initODBC(). This creates the ODBC environment handle and gets you ready to go. Before you send any queries to the database, you'll need to connect to it using the openConnectionODBC() function (see below for details). This will return the id for the connection handle. You'll need this to send queries.
At the end of your program, you should call cleanUpODBC(). Failure to do so may lead to resource leakage.
To run a query, use execDirectODBC(). Any data returned will be passed as a sequence. If there is an error, the return will be a negative atom. You can call odbcError() with the handle that caused the error (connection, transaction, etc--it will be returned as a negative atom from the function in which the error occured).
Inserting, deleting and updating data can be done using SQL commands. If you have many records to insert, you should use parameters, since this will generally be faster than building a SQL command and inserting the proper values over and over (see prepareSQL, bindParameter and executeSQL).
v1.34 * Added closeConnectionODBC() (thanks to Andres Cabezas)v1.33 * Renamed to odbc.e: Jonas Temple added support for Linux using UnixODBC * Fixed problem with dataSourcesODBC() (thanks to Jonas Temple) * Added data types * Use SQLFetchScroll instead of deprecated SQLExtendedFetch * Improved error reporting to cover other return codes * odbcError() no longer calls message_box(), since this is Win32 only. Instead it prints to STDERR * moveToRecord() now returns an atom on error for better error handling. * Demo converted to wxEuphoria so that it's cross platform. * Fixed memory leaks in prepareSQL(), getColumnHeaders() and getData() * Added rowCount() * initODBC() now a function in order to verify that ODBC properly initialized. * execDirectODBC() now returns all data regardless of calls to setMaxRecords, so that handles are properly freed
v1.32.1 * Fixed bug in moveToRecord() when record had NULL fields
v1.32 * Added handling for SQL_TYPE_DATE to convertData() and revertData() Returns { Y, M, D } (I think)... * Added SQL_TYPE_TIMESTAMP (used my MS Access) to return YYYY-MM-DD HH:MM:SS
v1.31.1 * Fixed resource leak in execDirectODBC() (thanks to Josef Jindra) * Fixed zero-length string error in convertData() (thanks to Josef Jindra)
v1.31 * Fixed bug in createCursor() that didn't take into account the new behavior of getColumnHeaders() * Added getErrorODBC() to allow more flexible error handling
v1.3 * getColumnHeaders() no longer returns the headers in an extra layer of sequence * Added routines for inserting data * Added dataTypeName()
v1.2 * Added ability to compile SQL without executing and set parameters * Rollback and Commit transactions * Cursors * Converts SQL_NUMERIC and SQL_DECIMAL values * Improved connection options * Removed Win32Lib dependency from the library (the demo still uses it, though)
v1.1 * Get partial chunks of data. * Execute a SQL statement without returning data.
If you want to scroll through a data set, you must use a cursor. This is handy for applications that allow a user to navigate through a table's contents using a form, viewing and changing data as they go. It may also be a very fast way for an application to look through a table and change many records.
A cursor is distinct from the data you would get back from a SQL query run through executeSQL(), for example, though a cursor is still based on a SQL statement.
atom StatementHandle, integer ParameterNumber, integer InputOutputType, integer ValueType, integer ParameterType, integer ColumnSize, integer DecimalDigits, object ParameterValue )
bindParameter binds a buffer to a parameter marker in an SQL statement. ParameterNumber refers to the nth parameter in the statement. Parameters are referenced by the order in which they appear in the statement:
SELECT NAME, ADDRESS, STATE FROM EMPLOYEES WHERE NAME LIKE ? AND AGE > ?The value for NAME would be parameter 1, and the value for AGE would be parameter 2.
For example, to set the value for NAME to be "A%" (all names starting with "A") and the value for AGE to be greater than 35:
ok = bindParameter( hstmt, 1, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_CHAR, 50, 0, "A%", SQL_NTS ) ok = bindParameter( hstmt, 2, SQL_PARAM_INPUT, SQL_C_LONG, SQL_NUMERIC, 2, 0, 35, 4 )
See Also: cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Frees the resources allocated by the ODBC drivers. This must be called at the end of a session, or resources could be leaked.
See Also: bindParameter, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Close a database connection and release its resources. This procedure automatically calls freeHandleODBC() on the connection.
See Also: bindParameter, cleanUpODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Attempts to commit the current transaction. (See also rollback)
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
This creates a navigable recordset based on the contents of sql. Use getRecord() and moveToRecord() to navigate. To be able to view and change the entire contents of table EMPLOYEES:
cursor = createCursor( myConn, "select * from employees" )The return value is actually a statement handle, which the application must free ( freeHandleODBC ) when it is done with the cursor.
See Also: getRecord, moveToRecord, setField, setRecord, updateRecord
Returns the User Data Sources. The return sequence is the form of:
{{ "DSN Name 1", "Description Type" }, { "DSN Name 2", "Description Type" }}The first element is the text to pass to openConnectionODBC()
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Returns the name of an ODBC datatype that can be used in a sql create statement.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Returns the results of query sql_text. This function ignores the settings made by setMaxRecords. If no errors occur, execDirectODBC frees the statement handle it creates. If there is an error, a negative handle is returned, so that the application can query for errors. The returned handle may be either the statement or the connection, if there was an error in allocating the handle. The statment handle (if one was created) must then be freed by the application ( freeHandleODBC) to avoid resource leakage.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Executes a SQL statement that has already been processed by prepareSQL().
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Frees an ODBC handle. You should call closeConnectionODBC() on a connection handle.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
SQLFreeStmt stops processing associated with a specific statement, closes any open cursors associated with the statement, discards pending results, or, optionally, frees all resources associated with the statement handle. Valid flags are:
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Pass the handle for the statement in question, and a sequence of column headers will be returned. If hstmt is 0, uses the current handle. The global sequence last_datatype will contain the data types for each column.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Returns the current ODBC handle in use.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Return the next block of data from statement hstmt. Use hstmt = 0 to use the current handle.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Returns a sequence containing the error number as the first element, and a destription of the error as the second element.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Returns the values contained in the current record.
See Also: createCursor, moveToRecord, setField, setRecord, updateRecord
Initializes the library. Must be called prior to any other function. Returns 0 if ODBC is not available.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Inserts data into an ODBC table. This is for inserting multiple rows at a time. You can use insertRow() if you are only inserting one row.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Inserts data into an ODBC table.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
See Also: createCursor, getRecord, setField, setRecord, updateRecord
Displays the error result returned by the ODBC driver to STDERR.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Establishes a connection to a DSN. Returns the integer id of the connection.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
SQLDriverConnect is an alternative to SQLConnect. It supports data sources that require more connection information than the three arguments in SQLConnect, dialog boxes to prompt the user for all connection information, and data sources that are not defined in the system information.
A connection string has the following syntax: connection-string ::= empty-string[;] | attribute[;] | attribute; connection-string empty-string ::= attribute ::= attribute-keyword=attribute-value | DRIVER=[{]attribute-value[}] attribute-keyword ::= DSN | UID | PWD | driver-defined-attribute-keyword attribute-value ::= character-string driver-defined-attribute-keyword ::= identifier
Keyword | Attribute value description |
DSN | Name of a data source as returned by SQLDataSources or the data sources dialog box of SQLDriverConnect. |
FILEDSN | Name of a .dsn file from which a connection string will be built for the data source. These data sources are called file data sources. |
DRIVER | Description of the driver as returned by the SQLDrivers function. For example, Rdb or SQL Server. |
UID | A user ID. |
PWD | The password corresponding to the user ID, or an empty string if there is no password for the user ID (PWD=;). |
SAVEFILE | The file name of a .dsn file in which the attribute values of keywords used in making the present, successful connection should be saved. |
hwnd enables the Driver Manager to display dialogs (if required and allowed) to prompt the user for additional information to build the connection string.
The Driver Manager constructs a connection string to pass to the driver in the connect_string argument of the driver's SQLDriverConnect function. The Driver Manager does not modify the InConnectionString argument passed to it by the application.
The action of the Driver Manager is based on the value of the driver_completion argument:
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Compiles a SQL statement for later execution and returns the ODBC statement handle id. Queries that will be run multiple times should typically be prepared prior to excecution, and executed using executeSQL(). This can save a significant amount of time for frequently run queries over execDirectODBC().
The statment handle must be freed by the application to avoid resource leakage ( freeHandleODBC).
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Attempts to rollback the current transaction to the last commit.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Returns the number of rows in the dataset.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Same as execDirectODBC(), but runDirectODBC() does not return any data. You must use getColumnHeaders() and getData(). This function returns an ODBC statement handle, which must be freed by the application ( freeHandleODBC).
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, setMaxRecords, setParameter, SQL_SUCCEEDED, tableList
Update field number fieldnum with the value field for the current record. This does not save the changes to the database. You must call updateRecord() to save changes.
See Also: createCursor, getRecord, moveToRecord, setRecord, updateRecord
Sets the maximum number of records that will be returned by getData().
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setParameter, SQL_SUCCEEDED, tableList
Change the value of an already bound parameter. bindParameter() must be called for parameter number paramnum before calling setParameter().
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, SQL_SUCCEEDED, tableList
Update the changes to the current record. record must contain all of the field values for the record. This does not save the changes to the database. You must call updateRecord() to save changes.
See Also: createCursor, getRecord, moveToRecord, setField, updateRecord
Tests for a successful return code from a call to an ODBC API function.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, tableList
Returns a statement handle of a query whose data are table names contained within the database specified by hconn.
See Also: bindParameter, cleanUpODBC, closeConnectionODBC, commit, dataSourcesODBC, dataTypeName, execDirectODBC, executeSQL, freeHandleODBC, freeStmt, getColumnHeaders, getCurrentHandle, getData, getErrorODBC, initODBC, insertBulk, insertRow, odbcError, openConnectionODBC, openDriverConnectionODBC, prepareSQL, rollback, rowCount, runDirectODBC, setMaxRecords, setParameter, SQL_SUCCEEDED
Saves any changes made to the current record by setRecord() or setField().
See Also: createCursor, getRecord, moveToRecord, setField, setRecord
func
] proc
] func
] func
] func
] func
] func
] func
] func
] proc
] proc
] func
] func
] func
] func
] func
] func
] func
] func
]
] func
] proc
] func
] func
] func
] func
] func
] func
] func
] proc
] proc
] func
] func
] func
] func
]