Kylix Databases Programming

Embed Size (px)

Citation preview

  • 8/7/2019 Kylix Databases Programming

    1/40

    CHAPTER 6

    Overview of DatabaseDevelopmen

  • 8/7/2019 Kylix Databases Programming

    2/40

    Adatabase is a collection of one or more files used to store information in a struc-

    tured format. A database may be located on the same machine as your Kylix ap-plication, or another machine on the network to which the machine running your

    Kylix application is attached.

    This chapter is designed to provide you with an overviewof database development inKylix. It begins with a brief discussion of database terms and basic issues, including howdatabases are created. This is followed by an overview of the database architecture pro-vided by Kylix. Next, the discussion turns to an overview of the various components thatyou use to build your Kylix database applications.

    One of the more important database-supporting features in Kylix is DBExpress, aframework used to access data managed by a database server (a separate applicationused to manage a database). The use of DBExpress requires some configuration, which isthe focus of the latter part of this chapter. Finally, this chapter concludes with astep-by-step demonstration of building a simple database application using Kylix.

    If you are new to database development, you will want to read this chapter thor-

    oughly. If you are a seasoned database developer, but new to Kylix, you can skip the firstsection Understanding Databases, and continue on to the section Overview of DataAccess in Kylix.

    This chapter is intended as an overview, in that it does not go into detail about usingthe various database-related components provided by Kylix. The use of these componentsis covered in depth in the next four chapters of this section. For example, in Chapter 7,Working with Data-Aware Controls, you will learn how to configure and enhancemany of the powerful data-aware controls in Kylix. The TField class and its descendantsare discussed in Chapter 8, Working with TFields. Chapter 9, Using DataSets, takesan extended look at the TDataSet descendants. Finally, in Chapter 10, Advanced Data-base Techniques, you will learn how to make the most of TClientDataSets in a distrib-

    uted environment.As mentioned already, DBExpress is the mechanism that permits Kylix to access datamanaged by a database server. DBExpress is an open architecture, meaning that anyonewith the time and resources can create new DBExpress drivers. You might want to do thisif your data is managed by a database server that is not already supported by existingDBExpress drivers. In Chapter 11, Writing DBExpress Drivers, you will find a detaileddescription of the DBExpress interfaces, which you can implement to create your ownDBExpress drivers.

    UNDERSTANDING DATABASESIf you are new to working with database applications, some of the terms may be unfamil-iar to you. This section is designed to give you are brief introduction to concepts usedthroughout these database-related chapters. If youare already comfortable with buildingdatabases, you will want to scan this section quickly, spending more time instead on thesections that follow this one.

    2 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    3/40

    Databases and TablesThe term database, as it is used here, refers to one or more data structures, called tables, thatcontain data pertaining to a particular application.This data is typicallyaccessed througha relational database management system (RDBMS). Examples of RDBMSs include

    InterBase, Oracle, mySQL, DB2, and so forth. However, a database may exist without aRDBMS. For example, using Kylix you can create one or more structured files on the localfile system to hold your data. Using the preceding definition, these files would constitutea database as well.

    A database consists of one or more tables, a table being a structure capable of han-dling various types of data, including textual information, numbers, dates, binary data,and so on. Some RDBMSs use the term file instead of table. The concept, however, is thesame in that both contain structured information. Since the contents of the table may ap-pear in either a single file or separate files, this book uses the more generic term table.

    Each table in a database is designed to hold data related to a particular object, concept,or relationship. For example, a sales database, like the one represented in Figure 6-1, may

    include onetable to hold allof the information about customers. This information mayin-clude the customers account numbers, names, mailing addresses, available credit limits,and so forth. Another table may be designed to hold information about employees, in-cluding their names, addresses, positions, salaries, birth dates, and so on. Yet another tablemay hold information about sales. Examples of information that this table may containinclude the invoice numbers, dates of sales, customers to whom the sales were made, andemployees responsible for the sales. The sales table in this preceding example can be con-sidered to hold a relationship, or association, between a customer and an employee.

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

    Figure 6-1. A simple database designed to hold sales information

  • 8/7/2019 Kylix Databases Programming

    4/40

    Tables are organized by records and fields (these are sometimes referred to as rows andcolumns, respectively. The terms records and fields are used in this book). A table containsone field for each type of information stored in that table. For example, one field stores acustomers account number andanother storesa customers credit limit. In addition,eachfield has a particular data type, which is similar to the concept of declared Pascal types.

    However, unlike Pascal types, which are defined by either the compiler or a type declara-tion block, the data type of a field is limited to those predefined SQL data types availableon the particular database server. Some RDBMS allow users to define their own datatypes, which are generally referred as UDTs (user-defined types). Oracle, for example,supports fields of abstract types while InterBase tables do not. All databases, however,support certain common column types, including text, integers, real numbers, dates, andso forth. The number and type of columns contained within a given table is referred to asthat tables structure.

    A given table can contain zero, one, or more records, each record representing one ofthe items or relationships being stored in the table. For example, if your table contains in-formation about 1,000 customers, your customer table will contain 1,000 records. A table

    with zero records is referred to as an empty table.It is not at all uncommon for the number of records in a table to fluctuate. For exam-

    ple, this week our customer table may contain 1,000 customers, and next week it mightcontain 1,100. Furthermore, tables can potentially store a very large amount of data. Ta-bles with millions of records of data are not rare. The number of fields a table has, by com-parison, is more or less fixed (changing the number of fields is something that is typicallydone only by the database administrator, and can have important consequences for anyKylix application that uses persistent fields to access the data). Furthermore, the maxi-mum number of fields is relatively low, generally being less than 1,000 fieldsand nor-mally far fewer (this depends on the needs of the database). In most cases tables have onlya few fields, rarely exceeding several dozen or so.

    Databases and SQLThe Structured Query Language (SQL) is theprimary language forselectingandmanipu-lating data stored in RDBMSs. Consequently, it should be no surprise that this is also thelanguage that you will use most of the time when you need to access data from anRDBMS using DBExpress. (The alternatives to using SQL are to use stored procedures,which are described a little later in this chapter, or to use table access, in which SQL is gen-eratedforyouby an appropriate DataCLX component, such as theSQLTable component.)

    SQL statements can be divided into two general categories: data manipulation lan-guage (DML) statements and data definition language (DDL) statements. Data manipu-

    lation language statements permit you to select and change the contents of tables. Thesestatements include select, update, delete, and insert.

    Data definition language statements, on the other hand, are used to define and alterdata structures and other related database objects like views, indices, and so forth. For ex-ample, you use the DDL statement create table to create a new table in a database,alter table to change a tables structure, and so forth.

    4 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    5/40

    While most RDBMSs roughly conform to ANSI SQL92 (the current standard), mostRDBMSs include slight variations or extensions that permit unique features particular tothat RDBMS to be exploited. What this means is that while the differences between thedifferent dialects of SQL are often minor, you cannot assume that one SQL statement willnecessarily work with all RDBMSs. However, if you keep your SQL simple, and try to

    avoid using a feature that is particular to a specific RDBMS, your SQL should be portablefor the most part. If portability (the ability to transparently change which RDBMS you areusing) is not important, you will simply use the dialect of SQL appropriate for your se-lected database server.

    Although this chapter, and the next four that follow it, will include many different ex-amples of SQL statements, this book does not cover the SQL language. For more informa-tion on using SQL, please refer to the documentation for your particular RDBMS.

    Other Database-Related ConceptsAnother critical concept associated with a table is an index. An index is a support struc-

    ture (sometimes represented by a separate file) that adds additional organization to a ta-ble. This organization provides a number of benefits, including record sorting, improvedrecord selection, faster table joins, and, in some cases, guaranteed record uniqueness. Agiven index may be associated with a single field in a table, such as employee number.Depending on your needs, however, an index may be based on multiple fields. For exam-ple, if you often need to execute a SQL select statement to choose employees by jobtitleand department, you will benefit from having an index based on these two fields. (ManyRDBMSs even permit indexes to be based on expressions, or calculations, applied to oneor more fields.)

    Indexes that enforce uniqueness among records are important to prevent two or morerecords from sharing the same critical identifier. For instance, since it is unacceptable for

    a bank to give two different customers the same account number, the customer tablewould likely include a unique index that ensures that the values in the account numberfield are unique.

    In addition to indexes, a DBMS may include a number of other logical data structureslike constraints, views, and stored procedures, to name a few. Constraints are rules thatdefine what constitutes an acceptable field in a record. For example, a constraint can beused to define that only non-null values may be entered into a particular field, such as ac-count number. This constraint would prevent a customer record from being added to thetable with an empty account number.

    Views are similar to tables, in that they consist of records and fields. In fact, a view isdefined based on one or more tables, giving a customized view of the data. A particular

    view may contain fewer records and fields than the table or tables on which it is based. Inother words, a view is like a stored query.

    Stored procedures are subroutines that reside on a RDBMS (although not all RDBMSssupport stored procedures). When available, stored procedures offer two primary ad-vantages over SQL queries. First, they are defined onceon the RDBMSbut can beused many times, by many different client applications, without having to be redefined

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    6/40

    by each application.Second, in general they provide improved performance over compa-rable SQL queries. Specifically, an RDBMS can more efficiently execute the statements ina stored procedure, compared to a comparable SQL query.

    Stored procedures typically include one or more SQL statements, although they canalso make use of proprietary keywords, depending on the RDBMS. For example,

    InterBase stored procedures, which consist primarily of SQL, may also include InterBaseprocedure language statements. The InterBase procedure language provides controlstructures (if, for select do, and so forth), statement blocks, and other languageelements that permit the creation of more sophisticated statements than can be declaredusing SQL alone.

    About the Database Used in This BookThe tables used in the examples presented in this book are sample InterBase tables foundin the employee.gdb database. This database is installed when you install the InterBaseserver found on your Kylix CD-ROM. If you selected the default installation location,

    this database is located in the /usr/local/interbase/examples directory. This da-tabase includes a number of related tables, including customer, employee, department,and sales. It also includes a number of predefined stored procedures that operate onthese tables.

    Creating Databases and TablesAs mentioned earlier, Kylix provides you with support for two general categories of da-tabase applications: databases that are based on local files (either XML-based or a binaryformat) and databases that are managed by an RDBMS. If you are creating a localfile-based database, you use the properties and methods of the TClientDataSet class. This

    process is described in detail in Chapter 9, Using DataSets.When you need to create a database and its associated tables for an RDBMS, the pro-cess is more involved. When you install InterBase, it installs several sample databases, in-cluding one called employee.gdb. While this database is fine for the sampleapplications demonstrated in this book, when creating a new database application youwill need to create a completely new database, as well as design the tables to hold the dataspecific to your needs.

    There are two general approaches you can take to creating a new database for anRDBMS. The first, and most common, approach is to use the tools associated with the par-ticular RDBMS to create your database, tables, indexes, stored procedures, and so forth.For example, InterBase includes the utility isql, which permits you to enter isql com-

    mands to define databases, tables, and other related definitions. This utility can either beused interactively, or it can be used to execute isql commands stored in a file. For infor-mation on using isql, see the InterBase documentation that is installed when you installInterBase. (This documentation is provided in Adobe Acrobat format. A version ofAdobe Acrobat Reader for Linux is also provided.) If you are using any other RDBMS, seethe documentation that accompanies that database for information on its use.

    6 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    7/40

    The second approach is to use the SQLDataSet or SQLQuery component on theDBExpress page of the Component palette. Using either of these components, you set theCommandText property to the SQLDDLstatementssuchascreate database, cre-ate table, or create indexthat you want to execute, and then call the Executemethod. This second technique is particularly useful when you want to create new tables

    in an existing database during runtime.It should be noted that the proper design of the tables and indexes of your database is

    a very important, and sometimes time-consuming process. If you are unfamiliar with da-tabase design, and relational database design in particular, you should consult a book onthe design and analysis of databases prior to creating your tables. Alternatively, arrangeto work with someone who has database design experience.

    OVERVIEW OF DATABASE DEVELOPMENT WITH KYLIXKylix is a general application development tool, as opposed to strictly a database devel-

    opment tool. However, one of the essential themes behind its evolution has been data-base development. This is obvious when you consider the name of its WindowsancestorDelphi. Delphi is the Greek city where the oracle of the god Apollo was lo-cated, Oracle also being the name of one of the worlds leading RDBMSs.

    In the original architecture, Delphi was designed to be a world-class development en-vironment that provides high-end support for database development. This was achievedthrough a collection of data access classes that used the Borland Database Engine (BDE)for accessing data in combination with a small but powerful collection of data-aware con-trols. This combination permits database developers to quickly build high-performancedatabase applications using a RAD (rapid application development) approach, wherelow-level dataaccess operations are encapsulated in easy-to-configure dataaccess compo-

    nents. As a result, developers can focus on implementing the specific features of the data-base application, rather than struggling with the mundane chores associated with writingdirectly to the RDBMS vendor client library for record locks and data reads and writes.

    This legacy of database support continues with Kylix, although without the BDE.While the BDE was a remarkable piece of software when it was first introduced in theearly 1990s, it earned a reputation for being a challenge to configure and install. In itsplace Kylix provides DBExpress, a lightweight open architecture for accessing data man-aged by RDBMSs. Applications based on DBExpress have a smaller overall footprint, aremuch easier to configure, support faster data access, and have the potential to be ex-panded to a much wider range of database back ends.

    Types of Database Applications Supported by KylixThere are four general approaches used for the creation of database applications thatKylix supports. These are direct file access, local tables, DBExpress-based, and DataSnap(formerly known as MIDAS, multitier distributed application services). Each of these ap-proaches is discussed separately in the following sections.

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    8/40

    Direct File AccessDirect file access refers to the process of programmatically reading physical files from thelocal file system, and managing the data stored in them. These files can be simple binaryor ASCII files, or they can be typed files where the data is stored as a series of records,

    where record in this case refers to a declared Pascal record type. Figure 6-2 represents thegeneral architecture of this type of application.The process of creating a database application using direct file access is a labor-inten-

    sive one. In short, as a developer you are responsible for every aspect of the data access.Before any data access can occur, the data must be read from one or more files and storedin memory. Examples of memorystructures that youmight use include memorystreams,StringLists, arrays of records, and so forth.

    If you want to display this stored data to an end user, you must also populate one ormore visual components. If these components represent a view of a single record, you arelikely to use one or more components such as Edits, MaskEdits, ComboBoxes, Memos,and so on. If you want to display more than one record at a time, a component such as a

    StringGrid can be used.

    8 Kylix Developer's Guide

    Figure 6-2. Using direct file access, you use standard file I/O routines to read and write data.

  • 8/7/2019 Kylix Databases Programming

    9/40

    The following code sample comes from the DirectAccess application with this book'scode samples, which demonstrates one way in which this can be accomplished. Considerfirst the following type declaration, which declares a record type named TCustomer:

    L 6-1 type

    TCustomer = recordName : string[50];

    AccountNo : string[30];

    CreditLimit: Integer;

    end;

    This declaration is used to declare a typed file of this type. This declaration is found inthe following code segment, which is executed when the application starts:

    L 6-2 procedure TForm1.FormCreate(Sender: TObject);

    var

    cust: TCustomer;

    F : file of TCustomer;

    row: Integer;

    begin

    row := 1;

    StringGrid1.RowCount := 2;

    FDataFile := 'custs.dat';

    StringGrid1.Cells[0, 0] := 'Customer Name';

    StringGrid1.ColWidths[0] := 175;

    StringGrid1.Cells[1, 0] := 'Account No';

    StringGrid1.ColWidths[1] := 120;

    StringGrid1.Cells[2, 0] := 'Credit Limit';

    StringGrid1.ColWidths[2] := 80;

    StringGrid1.FixedRows := 1;

    if FileExists(FDataFile) then

    begin

    AssignFile(F,FDataFile);

    Reset(F);

    try

    while not Eof(F) do

    begin

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    10/40

    Read (F, cust);

    StringGrid1.Cells[0, row] := cust.Name;

    StringGrid1.Cells[1, row] := cust.AccountNo;

    StringGrid1.Cells[2, row] := IntToStr(cust.CreditLimit);

    Inc(row);

    StringGrid1.RowCount := row;end;

    finally

    CloseFile(F);

    end;

    end;// if FileExists...

    end;

    Youll notice that this code begins by setting a number of properties of the StringGrid,including the size and captions for the first row, which is a fixed row (and therefore can-not be edited). Next, if a data file already exists, it is opened and the previously stored

    data is read from it. In this case, rather than populating a stand-alone memory structure,the data is written to the StringGrid (which is serving both as a memory structure forholding the data and as a visual control for navigating and editing the data).

    When you are writing applications that use direct access, if your user interface dis-plays only one record at a time, you will also want to provide the end user with a meansof navigating the data using a tool bar, a menu, a collection of buttons, a search field, orsome other mechanism. And when the user makes a selection to navigate, your codemust repopulate the visual controls with the newly arrived record.

    Things get even more complicated if the end user is allowed to edit the data you dis-play. Specifically, you must detect that the user has changed a record and update thein-memory representation. Finally, any changes made to the data must be written back to

    the file or files when the user is through. The following code demonstrates how this fea-ture is implemented in the DirectAccess example:

    L 6-3 procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);

    var

    Cust: TCustomer;

    F : file of TCustomer;

    row: Integer;

    begin

    if FModified then

    if MessageDlg('Save Changes',mtConfirmation,mbOkCancel,0) = mrOK then

    begin

    AssignFile(F,'custs.dat');

    Rewrite(F);

    try

    for row := 1 to Pred(StringGrid1.RowCount) do

    begin

    10 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    11/40

    Cust.Name := StringGrid1.Cells[0, row];

    Cust.AccountNo := StringGrid1.Cells[1, row];

    Cust.CreditLimit := StrToInt(StringGrid1.Cells[2, row]);

    Write (F, Cust);

    end;

    finallyCloseFile(F);

    end;

    end; //if MessageDlg...

    end;

    You can find this code in a simple project named DirectAccess in the directaccesssubdirectory at Osbornes Web site (www.osborne.com).

    In this code example, a field named FModified identifies whether or not any of the datahas been changed in the StringGrid. If changes have been made, the code opens the typeddata file (creating it if is had not yet been created), and writes the contents of the StringGrid

    to this file.This description of direct access presented so far assumes that only a single user can

    access the data files. If two or more users (or applications) can be permitted to access thedata simultaneously,your code must also be prepared to resolve competition forrecords.For example, what if two different users make a change to the data? How do you ensurethat the changes by one user do not overwrite changes by another? It can be done, but youmust implement this feature manually.As a result, most direct file access applicationsaresingle-user applications, where only one user can access the data anyway. Consequently,most applications of this type do not have to manage competition for records.

    But there are additional features that you normally find in a database that you mustimplement yourself when using direct file access. Two of these are indexes and con-

    straints. If you want to provide for alternative sort orders, you must provide for this fea-ture programmatically. Likewise, any constraints that you want to apply to the data willbe the result of your code testing each record explicitly. Consider the following code,which is found in the StringGrids OnSetEditText event handler:

    L 6-4 procedure TForm1.StringGrid1SetEditText(Sender: TObject; ACol,

    ARow: Integer; const Value: String);

    begin

    if ACol = 2 then

    begin

    try

    StrToInt(Value);

    except

    raise Exception.Create('Credit limit must be an integer value');

    end;

    end;

    FModified := True;

    end;

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    12/40

    This code evaluates which column of the StringGrid has been edited. If the third col-umn (columns are zero based, so column 2 is the third column), the data is checked tomake sure that it contains a valid integer.

    Another feature that you may want is security. If you do, this too must be imple-mented manually. This would involve encrypting the data before writing it to the file,

    and decrypting it while loading it into memory.After reading this description of theprocess of creating directaccess applications, you

    might ask, Why would anyone bother to use direct file access for their database applica-tion? The answer is that you can completely customize the experience. You are not lim-ited to using the data-aware controls, and you can define the data access mechanism anyway you like. In addition, since you are using Kylixs basic file I/O (input/output) rou-tines,youcanprovide completely self-contained data access. Allof the other mechanismsfor data access require some type of external file, even if it is a simple shared object file,which in turn creates a somewhat more complicated installation process.

    On the other hand, using direct file access is definitely not the RAD way of doingthings. The power of component-based development is derived from relying on the fea-

    tures encapsulated in components, such as data-aware controls. These controls performmany of the mundane tasks, including automatically updating their displayed data in re-sponse to a users record navigation.

    In short, using direct file access is not the Kylix way. It is available, however, and isappropriate for those select applications that require the benefits that this approach pro-vides, and that are worth the extra trouble that their implementation entails.

    Local TablesLocal table applications are those that use the LoadFromFile and SaveToFile features ofthe TClientDataSet to read and write files. These files, which are also stored on the local

    file system, contain data either in a binary format or in XML. The basic architecture of thistype of application is depicted in Figure 6-3.

    While at first glance this might just sound like an alternative that is little differentfrom direct access, this is not the case. There are a number of important advantages of us-ing local tables over direct access.

    First, you do not have to use custom type declarations to use local tables. Instead, youdefine the structure of your tables using either the FieldDefs property of the TClientDatasetclass, or by creating design-time TFields. The physical storage of the data is automaticallyhandled by the component.

    Second, TClientDataSet instances are TDataSet descendants. This important factmeans that you can use Kylixs data-aware controls to display, edit, and navigate your

    data. Likewise, one-to-many relationships between multiple data files can be depictedautomatically, requiring no code whatsoever.

    But being a TDataSet descendant has far greater implications than simply reducing theoverhead of the user interface. Client datasets implement the many convenience propertiesand methods of TDataSet class, including those that provide for features such as indexes,

    12 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    13/40

    ranges, filters, locates, and constraints. Consequently, data displayed by local tables can beeasily customized, and much of this customization can be defined at design time, usingproperties rather than relying on runtime code. The result is much faster application devel-opment combined with greater ease of maintenance.

    Local tables do have some drawbacks, however. First, they are designed for sin-gle-user applications, meaning that the data they manage is not shared. While this is gen-erally true of direct file access applications as well, it is a major limitation compared with

    DBExpress and DataSnap-based applications. Also, local table applications require thedeployment of at least one DataSnap-related shared object library (see Kylix documenta-tion for the name of this library). While the deployment of this library is not complicated,it is possible to create direct access applications that require no additional files.

    Another drawback to local table applications is that they do not support security. Ba-sically, whether you use binary or XML-based local tables, there is no way to encrypt thedata to prevent others from viewing it. In fact, you have fewer options here than youwould with direct file access. With direct file access, you can implement security, if neces-sary. You do not even have this option when using local tables.

    Some peoplemight also point out that you normally usedata-aware controls with lo-cal table applications, whereas this is not an option with direct access applications. The

    argument is that there are few data-aware controls and that these controls are less flexi-ble than some of their nonaware counterparts. In response, it should be noted that localtable applications do not require the use of data-aware controlsthey merely permit it.If your application needs display options not provided through the data-aware controls,

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

    Figure 6-3. Local tables make use of the TClientDataSet methods to read and write data.TClientDataSet is a TDataSet descendant, which permits these applications touse data-aware controls.

  • 8/7/2019 Kylix Databases Programming

    14/40

    you can use the data managed by a TClientDataSet to control the display properties ofany visual component. However, by doing so, you lose the ease of configuration thatmake data-aware controls so attractive in the first place.

    Applications Built Around DBExpressWhen you create an application that uses DBExpress, by definition you are not accessingthe data files directly, as you do with direct file access and local tables. Instead, you areworking through one or more shared object libraries to access data managed by aSQL-basedrelational database management system, such as InterBase or Oracle. Figure6-4represents the architecture of this type of application.

    Applications based on DBExpress have many of the same advantages that local tableapplicationshave, plus a wholeset of additional benefits. The similarities include makinguse of TDataSet descendants, which in turn enables the use of both data-aware controlsand the properties and methods of TDataSet, including ranges, filters, indexes, and soforth. In fact, when you use DBExpress, you often also use a TClientDataSet, either di-

    rectly or indirectly. The primary difference is that the data is not loaded by theTClientDataSet instance from a local file. Instead, it is obtainedthrough a provider interface.

    14 Kylix Developer's Guide

    Figure 6-4. DBExpress relies on external libraries to read and write data from a database server.

  • 8/7/2019 Kylix Databases Programming

    15/40

  • 8/7/2019 Kylix Databases Programming

    16/40

    keep the database in top running order. In addition, most RDBMSs represent an addi-tional cost. Oracle, for example, can be relatively expensive, depending on the number ofusers who have access to the database. Others, such as InterBase and mySQL, are opensource, and whether you must pay to use them depends on how they are being used.

    DataSnap ApplicationsDataSnap is Borlands n-tier framework for accessing data through an application server.While the initial release of Kylix does not support the development of DataSnap applica-tions, it does contain many of the components that are used in DataSnap applications.Borland plans to add DataSnap support in future versions of Kylix. As a result, onceDataSnap support becomes available in Kylix, existing applications based on DBExpresscan be upgraded to DataSnap with relative ease.

    The primary difference between DBExpress applications and those based onDataSnap is the mechanism used to populate a client dataset. Instead of loading datafrom a unidirectional dataset, the client dataset makes use of a special connection compo-nent to communicate using a network protocol such as TCP/IP or IIOP (InternetInter-Orb Protocol, used to communicate between CORBA (the common object requestbroker architecture), clients, and servers) to access a dataset provider running on aDataSnap application server. That dataset provider gets its data from a TDataSet descen-dant using any mechanism available to the DataSnap server. This relationship is shownin Figure 6-5.

    16 Kylix Developer's Guide

    Figure 6-5. DataSnap client applications get their data from a DataSnap server, which in turn canaccess data from local database files or through a database server.

  • 8/7/2019 Kylix Databases Programming

    17/40

  • 8/7/2019 Kylix Databases Programming

    18/40

    Another characteristic of DataSnap applications is data transparency. Specifically, theclient dataset on the DataSnap client receives the data in a source-neutral format. The cli-ent application does not know, nor does it matter, where the data came from. This per-mits you to change the type of database used by the DataSnap server at any time, withoutaffecting existing DataSnap clients.

    While Linux developers may have a preference to access DataSnap servers runningon Linux servers (once DataSnap server development is available in Kylix), it is nice tohave the option of connecting to a DataSnap server running on a Windows NT server or aWindows 2000 server. One of these advantages is that a Windows-based DataSnap servercan be designed as an MTS (Microsoft Transaction Server) object. This permits yourDataSnap server to benefit from MTS features such as just-in-time activation and data-base connection pooling.

    WhileDataSnapapplicationshave many advantages, this technology is not appropriatefor every application. In the first place, deployment of DataSnap servers requires the pur-chase of an additional license from Borland. While the license fee is relatively small, cur-rently around $300 per server, it is an unnecessary expense if the features of DataSnap are

    simply not needed. In addition, because you must create the DataSnap server as well as theclient, DataSnap-based applications are more complicated than corresponding DBExpressapplications.

    COMPONENTS USED IN DATABASE APPLICATIONSOf the four general techniques used to access data described in the preceding sections, lo-cal tables and DBExpress are the two that are most appropriate for building database ap-plications with the first release of Kylix. In this section, the components that you use tobuild these types of applications are described in detail. Some of these components are

    also used to build DataSnap applications, even though that feature is not yet available.Nonetheless, this will be mentioned in passing where appropriate.

    Data-Aware ControlsData-aware controls are the visual components that you typically use to construct theuser interface of your Kylix database applications. In reality, you could potentially buildyour user interface with any of Kylixs visual controls. However, data-aware controls areespecially useful since they interact with Kylixs other data-related controls to simplifyoperations such as table navigation, editing data, and posting changes. If you build yourdatabase applications user interface with controls other than the data-aware controls,you will also need to add code to manage these operations.

    The data-aware controls that come with Kylix are found on the Data Controls page ofthe Component palette. Each of these components is described in Table 6-1.

    18 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    19/40

    Ill 6-1

    All data-aware controls have a DataSource property. This property points to a datasource component, which in turn points to a dataset instance (either a client dataset or

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

    Component Description

    DBGrid A multiline grid for displaying the contents of a tableor the result set of a query or stored procedure.

    DBNavigator A ten-button control for navigating and changing the

    state of a dataset. Navigational buttons include FirstRe cord, Next Record, Last Record, and so forth. Statechanging buttons in clude Refresh, Insert, Post, and

    Can cel Changes.

    DBText A simple control for displaying the contents of a singlefield as a read-only label.

    DBEdit A single-field control for displaying and editing text,integers, dates, and other simple data values. Data ina DBEdit appears on a single line.

    DBMemo A single-field control for displaying the contents of alarge text field. DBMemos can be used to display twoor more lines of text from a single field.

    DBImage A single-field control for displaying bitmap images.

    DBListBox A single-field control for displaying and editing thevalue of a field. The list box typically lists all possiblevalues for the field, with the selected valuerepresenting the contents of the field in the table.

    DBComboBox A single-field control for displaying and editing thevalue of a field. The combo box drop-down list candisplay alternative values for the field, while the editfield of the combo box displays the current field value.

    Table 6-1. The Data-Aware Controls Available on the Data Controls Page of the Component Palette

  • 8/7/2019 Kylix Databases Programming

    20/40

    a SQL client dataset in this first release of Kylix). For data-aware controls that are not sin-gle-field controls, theDataSource property is theonly property that is required to connectthe component to data.

    Single-field controls also require a DataField property. This property points to theparticular field in the dataset whose contents are used to populate the display of the control.If the control permits editing of the data, this is the field to which data changes are posted.

    20 Kylix Developer's Guide

    Component Description

    DBCheckBox A single-field control for displaying and editing datain a two-state field. Checked indicates one state and

    unchecked indicates the other state.DBRadioGroup A single-field control for displaying and editing

    data in a multistate field. The possible field valuesare represented by radio buttons. Clicking one buttonin the group toggles off any other selected button,meaning that only one of the buttons, at most, can beselected at a time. No buttons selected represent a nullfield value.

    DBLookupListBox A single-field control for displaying and editingthe value of a field. DBLookupListBox is similarto DBListBox, except that the data in the list box ispopulated from a lookup table. For example, in anemployee database you may have a department fieldused to identify the employees department. If yourdatabase also includes a department table, listing alldepartments in the company, you can use the valuesin the department table to populate the possible valuesfor the department field in the list box.

    DBLookupComboBox A single-field control for displaying and editingthe value of a field. DBLookupComboBox is similarto DBComboBox, except that the values in the drop-

    down list are populated based on the contents ofa lookup table, in the same way as the list box ispopulated in a DBLookupListBox.

    Table 6-1. The Data-Aware Controls Available on the Data Controls Page of the Component Palette(continued)

  • 8/7/2019 Kylix Databases Programming

    21/40

    The two lookup components, DBLookupListBox and DBLookupComboBox, haveseveral additional properties that must be defined. These are ListSource, KeyName, andListField. Together these properties are used to define the dataset containing the lookupdata, the field to use for looking up, and the field whose value is displayed. Consider theexample of an employee database, where an employee table contains a department num-

    ber field, which holds a value that represents the department by number rather than byname. Assuming that there is a department table that includes a unique index by depart-ment number, as well as a field that contains the departments full name (for example,Accounting), the ListSource property would point to the data source that points to the de-partment table, the KeyName would name the department number field, and theListField would name the department full name field. In this situation, the user editingtheemployee table canusethelookupcomponent to select theemployees department byname, even though it will be the corresponding department number that is actuallystored in the employee table.

    You are not limited to only using the data-aware controls that come with Kylix.Shortly after Kylix ships there are likely to be data-aware controls available from a num-

    ber of third-party vendors. In addition, you can write your own data-aware controls, ei-ther by extending one of the available data-aware controls or by encapsulating one ofKylixs data link components (such as the FieldDataLink or GridDataLink) in a customcomponent that you define. For information on creating data-aware controls, refer toKylixs online help.

    For more information on configuring and using these data-aware controls, please re-fer to Chapter 7, Working with Data-Aware Controls.

    Data Access Components

    Data access components are the intermediate components for configuring data access inKylix. These components are found on the Data Access page of the Component palette.Each of these components is described in Table 6-2.

    Ill 6-2

    The data access components provide you with a wealth of features for navigating andupdating data. These features can be used in conjunction with data-aware controls to cus-

    tomize the user interface. Alternatively, when your application needs to edit data but hasno user interface requirements, the features of the data access components can be used di-rectly. For example, your code can access the data stored in a client dataset, make

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    22/40

    changes, and post those changes back, programmatically, without the use of data-awarecontrols. In fact, when data-aware controls are not necessary, you typically do not even

    22 Kylix Developer's Guide

    Component Description

    ClientDataSet The ClientDataSet component provides an in-memory datasetfor holding, navigating, and editing data. This data is obtained

    either from local tables or through a dataset provider attached toa unidirectional dataset. In DataSnap applications, ClientDataSet usesa remote connection component to attach to a dataset provider locatedon a remote data module of a DataSnap application server.ClientDataSet components actually maintain two data stores. Thefirst, named Data, contains the current status of all records retrievedfrom the dataset provider. The second, named Delta, contains anychanges made to Data since the data was fetched.

    DataSetProvider The DataSetProvider component provides an interface betweena client dataset and another dataset. In the case of DBExpressapplications, this other dataset is a unidirectional dataset. Theprovider has two primary roles. The first is to feed data from

    a dataset to the Data property of a client dataset. The second isto post the changes made to a client dataset back to the originaldatabase. In this operation, the dataset provider receives the contentsof the client datasets Delta property. The dataset provider can theneither use its internal resolver to automatically apply the changes tothe underlying database or you can control how the data is updatedby writing event handlers for the dataset provider.

    DataSource The DataSource component is a component that interfaces betweendatasets and data-aware controls. In almost every case, this datasetwill be either a client dataset or a SQL client dataset. The role of thedata source is twofold. First, it instructs data-aware controls to updatetheir state when changes are detected to the dataset, such as when

    the dataset scrolls to another record. Second, it permits a particulardata-aware control to query the dataset state, asking whether or notdata edits are allowed. For example, when a user attempts to changethe contents of a DBEdit, the DBEdit queries the data source, askingif the associated dataset is in a state (dsEdit or dsInsert) that permitschanges to the contents of the field. If the dataset is not in an editingstate, or cannot be placed in an editing state by the data source,the data source will inform the DBEdit to reject attempts tochange the data.

    Table 6-2. The Data Access Components

  • 8/7/2019 Kylix Databases Programming

    23/40

    need a DataSource component. As a result, many Kylix developers tend to consider theDataSource component part of the user interface, even though it is a nonvisual control.

    NOTE: It is worth noting that additional data access components will likely become available as Kylix

    gains popularity. Specifically, there is a good chance that one or more third-party vendors will custom-ize TDataSet descendants fordata access, using either dbExpress or some other mechanism. As longas these alternative data access components are implemented by TDataSet descendants, you will beable to use any of Kylixs data-aware controls and DataSource components to connect to the data for

    which these alternative mechanisms are designed. One important benefit of this architecture is thatany user interface you build with data-aware controls can easily be reconfigured to use an alternativedataset in the future.

    You can find many examples of how you can use the data access components inChapter 9, Using DataSets, and Chapter 10, Advanced Database Techniques.

    DBExpress ComponentsThe components that reside on the DBExpress page of the Component palette make di-rect calls to one or more classes that implement the DBExpress interfaces, or at least en-capsulate components that do. Each of these components is described in Table 6-3.

    Ill 6-3

    TheSQLConnection component represents the DBExpress connection to thedatabaseserver. In most applications, youwill have a singleSQLconnection, andallunidirectionaldatasets will share this connection. When the database server you are connecting to re-quires a separate connection for each dataset, the SQLConnection component can eithercreate the additional connections automatically or you can use multiple SQLConnectioncomponents, one for each dataset.

    Even if your database server supports multiple statements per connection, there aretimes when youwill want to include multiple SQLConnection components in your appli-cation. Specifically, when you want to access a database from more than one thread inyour application, you will want to use a separate SQLConnection for each thread that ac-cesses data. By using a separate SQL connection for each thread, you ensure that your

    threads will compete for table and record locks in the same manner that two different us-ers on the network compete for these locks.

    In addition to representing a connection to a database, you use the SQLConnectioncomponent to control transactions (for those database servers that support transactions).

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    24/40

    24 Kylix Developer's Guide

    Component Description

    SQLConnection A SQLConnection component represents a connectionto a database server using a DBExpress driver. Successful

    connection requires that the SQLConnection componentpass to the DBExpress driver the parameters required bythe database server. These parameters necessarily includethe database being attached to, username, password,domain, role, or any other information required by thedatabase server, depending on which server is beingattached to.

    SQLDataSet The SQLDataSet component is a general component forworking with any data through DBExpress. It can be usedto execute queries and stored procedures, and select entiretables. When the query or stored procedure returns a result

    set, or an entire table is selected, the SQL dataset returns ahigh-performance unidirectional cursor. This cursor can beused to navigate in a forward direction only. Any attemptto position this cursor to a previous record in a result setresults in an exception being raised.

    SQLQuery The SQLQuery component is used to execute a query, orin some cases, a stored procedure (depending on the typeof database server). Any result set generated by this queryreturns a unidirectional cursor. A SQL query is intendedto provide an interface compatible with VCL Query com-

    ponents, thereby simplifying the process of convertinga VCL application to DataCLX.

    SQLStoredProc The SQLStoredProc component is designed to executea stored procedure on the database server. Any result setgenerated by this stored procedure returns a unidirectionalcursor. Some RDBMSs, like Oracle, allow multiple resultsets to be returned from a stored procedure execution. Inthat case, dbExpress returns more than one unidirectionalcursor. The SQLStoredProc component is intended to providean interface compatible with the VCL StoredProc component,thereby simplifying the process of converting a VCL

    application to DataCLX.

    Table 6-3. The DBExpress Components

  • 8/7/2019 Kylix Databases Programming

    25/40

    On some RDBMSs (like Oracle or InterBase), each SQLConnection can support multipletransactions, using a special TTransactionDesc instance for each unique transaction.

    It is also interesting to note that while a unidirectional dataset requires at least oneSQL connection, it is possible to execute queries against a server with a SQLConnectioncomponent alone. Using the SQLConnection.Execute method, you can pass a query to beexecuted against the server, along with any required parameters and a TCustomDataSetinstance to hold the results (if the query generates a result set).

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

    Component Description

    SQLTable The SQLTable component is designed to generate a SQLselect statement that selects all fields and all records

    from the named table, and return a unidirectional cursor.This convenience component is ideal for small lookup tables,but caution should be used when a large amount of datais stored in the table. A SQL table component is intendedto provide an interface compatible with the VCL Tablecomponent, thereby simplifying the process of convertinga VCL application to DataCLX. For optimal performanceand control, developers should consider using a SQLQuerycomponent instead.

    SQLMonitor The SQLMonitor component uses the TraceCallbackEventproperty of the SQLConnection component to log the SQLcommands being sent through the dbExpress driver. Usethe SQL monitor to debug or optimize your applicationsinteraction with the RDBMS. The TraceFlags propertypermits you to selectively trace categories of SQL statements.

    SQLClientDataSet The SQLClientDataSet component is a compoundcomponent, encapsulating a client dataset, a datasetprovider, and a SQL dataset. Many of the more importantproperties and methods of these encapsulated componentsare exposed by the SQLClientDataSet component. As aresult, a SQL client dataset provides you with most of the

    power of these three components combined into a singleconfigurable component. If you intend to migrate yourDBExpress two-tier application to DataSnap n-tier at a latertime, it is probably better to use the three individualcomponents rather than the SQLClientDataSet.

    Table 6-3. The DBExpress Components (continued)

  • 8/7/2019 Kylix Databases Programming

    26/40

  • 8/7/2019 Kylix Databases Programming

    27/40

    Using DBExpress Conf FilesWhen you install Kylix, it creates a hidden directory named .borland under the samedirectory in which the kylix installation folder is created. For example, if you installedKylix as root, both the .borland and the kylix directories will be located under the

    /root directory.The.borland directory contains a number of configuration files (conf files), includingtwo that apply to DBExpress. These files are named:

    w dbxconnections

    v dbxdrivers

    These files contain definitions that can be used to configure SQLConnection components.The dbxdrivers file contains a list of the defined DBExpress drivers, along with ba-

    sic information for each driver, including the DBExpress driver library name, the vendorlibrary name, the database the driver will connect to, and so forth. This information is de-

    pendent on the driver type. Specifically, some drivers will have more driver parametersthan others. The following is the contents of the default dbxdrivers file when you firstinstall Kylix:

    L 6-5 [Installed Drivers]

    INTERBASE=1

    MYSQL=1

    [INTERBASE]

    GetDriverFunc=getSQLDriverINTERBASE

    LibraryName=libsqlib.so

    VendorLib=libgds.so.0

    BlobSize=-1

    CommitRetain=True

    Database=database.gdb

    Interbase TransIsolation=ReadCommited

    Password=masterkey

    RoleName=RoleName

    ServerCharSet=ASCII

    SQLDialect=1

    User_Name=sysdba

    WaitOnLocks=True

    [MYSQL]

    GetDriverFunc=getSQLDriverMYSQL

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    28/40

    LibraryName=libsqlmy.so

    VendorLib=libmysqlclient.so.6.0.0

    BlobSize=-1

    Database=DBNAME

    HostName=ServerName

    Password=passwordUser_Name=user

    [WaitOnLocks]

    False=1

    True=0

    [CommitRetain]

    False=0

    True=1

    [Interbase TransIsolation]

    ReadCommited=1

    RepeatableRead=2

    [SQLDialect]

    1=0

    2=1

    3=2

    The dbxconnections file contains information about stored connection configura-

    tion parameters. A connection represents the use of an installed driver to connect to a da-tabase. Consequently, some of the values listed in dbxconnections represent specificparameter overrides, compared to the data stored in the dbxdrivers file. For example,you might have two different InterBase databases that you regularly work with. Thedbxdrivers file will have only one InterBase-related driver entry (assuming that youhave only one DBExpress driver for InterBase, which is the case when you first installKylix), and this will represent the default information for this type of driver. By compari-son, the dbxconnections file will contain two entries, one related to each of theInterBase databases. At a minimum, the Database value will be different for the two dif-ferent InterBase connections, although other parameters, such as username and pass-word, may also differ depending on the security applied to each of the databases.

    The following is an example of the dbxconnections file as it appears when Kylix isfirst installed:

    L 6-6 [MySQLConnection]

    DriverName=MYSQL

    BlobSize=-1

    28 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    29/40

    Database=DBNAME

    HostName=ServerName

    Password=password

    User_Name=user

    [IBLocal]DriverName=INTERBASE

    BlobSize=-1

    CommitRetain=True

    Database=database.gdb

    Interbase TransIsolation=ReadCommited

    Password=masterkey

    RoleName=RoleName

    ServerCharSet=ASCII

    SQLDialect=1

    User_Name=sysdba

    WaitOnLocks=True

    The information in these two filesdbxdrivers and dbxconnectionscan beused to populate properties of the SQLConnection component. To demonstrate this, usethe following steps:

    1. Create a new project in Kylix.

    2. Add a single SQLConnection component from the DBExpress page of theComponent palette onto the main form.

    3. Using the Object Inspector, drop down the Driver property of the SQLConnectioncomponent and select INTERBASE. Once you do, you will notice that many of

    the other properties, such as GetDriverFunc, LibraryName, and VendorLib arepopulated with the definitions that were stored in dbxdrivers, as shown inFigure 6-6.

    Instead of using the DriverName property, you can use the ConnectionName prop-erty. Using the ConnectionName property will load not only the common propertiesfrom the dbxdriver file, but will also load the specific parameter overrides from thedbxconnections file.

    NOTE: If you have not made any changes to thedbxdrivers ordbxconnections files (ei-

    ther directly or using theDBExpressConnections Editor, described later in this chapter), youwill notbeable to use the preceding steps to actually connect to the InterBase server. This is because the Data-base parameter of these files points to a database named database.gdb, which does not existunless you have installed it or created it yourself. In the next section you will learn how to modify theconfiguration files to connect to the sample employee.gdb file that was installed when you in-stalled InterBase for Linux.

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    30/40

  • 8/7/2019 Kylix Databases Programming

    31/40

    begin

    SQLConnection1.DriverName := 'INTERBASE';

    SQLConnection1.ConnectionName := 'MyConnection';

    ExePath := ExtractFilePath(Application.ExeName);

    SQLConnection1.LoadParamsFromIniFile(ExePath + 'customconx');

    SQLConnection1.GetDriverFunc := 'getSQLDriverINTERBASE';SQLConnection1.LibraryName := 'libsqlib.so';

    SQLConnection1.VendorLib := 'libgds.so.0';

    SQLConnection1.Connected := True;

    SQLClientDataSet1.Open;

    The following is the contents of the customconx file, which is located in the same di-rectory as the application:

    L 6-8 [MyConnection]

    DriverName=INTERBASE

    BlobSize=-1

    CommitRetain=True

    Database=/usr/local/interbase/examples/employee.gdb

    Interbase TransIsolation=ReadCommited

    Password=masterkey

    RoleName=RoleName

    ServerCharSet=ASCII

    SQLDialect=1

    User_Name=sysdba

    WaitOnLocks=True

    You can find this code in the ByIni project in the connectionbyini subdirectory at

    Osbornes Web site.

    Configuring a SQLConnection Using ParametersInstead of using the contents of the dbxdrivers and dbxconnections files or a cus-tom connection file, you can provide the SQLConnection component with sufficient in-formation to access the DBExpress driver as well as the necessary parameters to connectto the database. If you use this technique, it is important to set the SQLConnection.LoadParamsOnConnect to False; otherwise, your application will attempt to reload theparameter values from a dbxconnections file. An example of how this might look isshown in the following code segment:

    L 6-9 SQLConnection1.DriverName := 'INTERBASE';

    SQLConnection1.GetDriverFunc := 'getSQLDriverINTERBASE';

    SQLConnection1.LibraryName := 'libsqlib.so';

    SQLConnection1.VendorLib := 'libgds.so.0';

    SQLConnection1.LoadParamsOnConnect := False;

    SQLConnection1.Params.Add('BlobSize=-1');

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    32/40

    SQLConnection1.Params.Add('CommitRetain=True');

    SQLConnection1.Params.Add(

    'Database=/usr/local/interbase/examples/employee.gdb');

    SQLConnection1.Params.Add('InterbaseTransIsolation=ReadCommitted');

    SQLConnection1.Params.Add('Password=masterkey');

    SQLConnection1.Params.Add('RoleName=RoleName');SQLConnection1.Params.Add('ServerCharSet=ASCII');

    SQLConnection1.Params.Add('SQLDialect=1');

    SQLConnection1.Params.Add('User_Name=sysdba');

    SQLConnection1.Params.Add('WaitOnLocks=True');

    SQLConnection1.Connected := True;

    SQLClientDataSet1.Open;

    You can find this code in the ByParams project in the connectionbyparams subdi-rectory at Osbornes Web Site.

    Editing the dbxdrivers and dbxconnections FilesThere are a number of ways to edit the DBExpress conf files, depending on which oneyou want to change. As far as the dbxdrivers file is concerned, you can modify this filemanually using an editor such as emacs, or it can be modified by a DBExpress driver in-stallation routine. You would modify this file manually if you wanted to change any ofthe default settings for any of the existing drivers. As you learned in the preceding sec-tion, the dbxconnections file uses the values from the dbxdrivers file to initializeconnection information, especially when you are adding new connections.

    WARNING: When adding a new DBExpress driver, it is preferable to permit the installation program

    to update thedbxdrivers file, if this option is offered. Some DBExpress drivers do not ship with aninstallation routine, but instead provide you with a sample dbxdrivers entry. To use this sample,merge its contents with the existing dbxdrivers file and then manually update the [InstalledDrivers] section.

    NOTE: To write your own dbxdriver installation routine, you can use Kylixs TIniFile class,which permits the reading and writing of conf files.

    While you can also modify the dbxconnections file manually, it is much more con-venient in Kylix to use the DBExpress Connection Editor. To display this editor, shown in

    Figure 6-7, either double-click a placed SQLConnection component or right-click aSQLConnection component and select Edit Connection Properties.

    32 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    33/40

    If you want to modify an existing connection from the DBExpress Connection Editor,select the name of the connection from the Connection Name list, and then modify thedisplayed parameters from the Connection Settings grid. This grid contains one entry foreach parameter permitted by the DBExpress driver used for the connection.

    To create a new connection, click the Add Connection button on the DBExpress Con-nection Editor toolbar. Kylix responds by displaying the New Connection dialog box.

    Ill 6-4

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

    Figure 6-7. Use the DBExpress Connection Editor to modify, add, or remove connections from thedbxconnections file.

  • 8/7/2019 Kylix Databases Programming

    34/40

    From the New Connection dialog box, select the driver you want to use from theDriver Name combo box, and then enter the name of the connection in the ConnectionName field. Click OK when you are done to return to the DBExpress Connection Editorwith the newly entered connection selected. Now use the Connection Strings grid to de-fine the values for the drivers parameters.

    To delete an existing connection, select the name of the connection you want to deletefromtheConnectionName list andthen click the DeleteConnection button onthetoolbar.

    Updating the IBLocal ConnectionThe following steps demonstrate how to update the IBLocal connection name to point tothe employee.gdb database that was installed when you installed InterBase. If youhave notyet installed InterBase, refer to Appendix C, Installing Kylix, InterBase, andtheSample Applications, before continuing.

    1. Create a new project, if necessary, by selecting File | New Application.

    2. Place a single SQLConnection component onto the main form.

    3. Right-click the SQLConnection component and select Edit ConnectionProperties. Kylix responds by displaying the DBExpress Connection Editor.

    4. Select IBLocal from the Connection Names list box.

    5. In the Connection Settings grid, select the Value column of the Database key.By default this value is database.gdb. Delete this entry and then enter thefull path and filename for the employee.gdb database that was installedwhen you installed InterBase. This file should be located in the /examplesdirectory under the interbase directory. If you use the default installationlocation, this full filename should be:

    /usr/local/interbase/examples/employee.gdb

    6. Close the DBExpress Connection Editor. Your connection should now allowyou to attach to the employee.gdb database. To test this, set the Connectedproperty of the SQLConnection to True. Since the SQLConnections LoginPromptproperty is set to True, Kylix will display the Database Login dialog box.

    34 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    35/40

    Ill 6-5

    Make sure that User Name is set to sysdba, and then enter masterkey in the Pass-word field. Click OK or press ENTER to continue. If the connection can be made, the Con-nected property will change to True, otherwise, an error message is displayed. If you getan error message, display the DBExpress Connection Editor again and correct the con-nection parameters.

    NOTE: The employee.gdb password is masterkey, which contains no spaces and is in all low-ercase letters.

    CREATING A SIMPLE DATABASE APPLICATIONSo far in this chapter you have been introduced to the concepts and components that youuse to create database applications. In this final section you will find the steps to placeandconfigure these components to create a simple database application. This applicationwill be based on DBExpress, and will display a single table. Because this application in-volves only one table and one form, a data module will not be used. Data modules are de-signedto share components between multiple forms,whichis notnecessary in this case.

    1. Create a new project.

    2. Place on this form one DBGrid and one DBNavigator from the Data Controlspage of the Component palette. Set the Align property of the DBNavigator toalTop, and the Align property of the DBGrid to alClient.

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

  • 8/7/2019 Kylix Databases Programming

    36/40

    3. From the Data Access page of the Component palette, place one ClientDataSet,one DataSetProvider, and one DataSource. Set the ProviderName propertyof the ClientDataSet to DataSetProvider1, and the DataSet property of theDataSource to ClientDataSet1.

    4. From the DBExpress page of the Component palette, place a SQLConnectionand a SQLDataSet. Your main form should now look similar to that shown inFigure 6-8.

    5. Set the SQLConnections ConnectionName property to IBLocal.

    6. Select the SQLDataSet and set its CommandType property to ctQuery. Next,select the CommandText property and click the Ellipsis button that appears inthe Value field. Kylix responds by displaying the CommandText Editor shownin Figure 6-9.

    36 Kylix Developer's Guide

    Figure 6-8. The components being used to create a simple database application

  • 8/7/2019 Kylix Databases Programming

    37/40

    7. Using the CommandText Editor, select CUSTOMER from Table Name andclick Add Table to SQL. Next, select the * character from Fields and click AddField to SQL. The resulting SQL statement should look like the following:

    select * from CUSTOMER

    This statement will select all fields and all rows from the CUSTOMER table inthe employee.gdb database. Click OK to close the CommandText Editorand save the SQL statement in the CommandText property. (If you do not havea CommandText property editor, simply enter select * from CUSTOMERinto the CommandText property.)

    8. Now select the DataSetProvider and set its DataSet property to SQLDataSet1.

    9. Finally, select the ClientDataSet and set its Active property to True. Doingthis will cause the DataSetProvider to access the SQLDataSet, which willattempt to connect the SQLConnection component to the database. Sincethe SQLConnection components LoginPrompt property is set to True, Kylix

    will display the Database Login dialog box. Enter the username sysdba andthe password masterkey.

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

    Figure 6-9. Use the CommandText Editor to create SQL queries against the tables in your database.

  • 8/7/2019 Kylix Databases Programming

    38/40

    If the username and password are correct, the SQL dataset will become active,thereby executing its query. The dataset provider will then read all of the query result setand package it into a variant array, and will then close the query by setting theSQLDataSets Active property to False. The dataset provider will then pass the data to theclient dataset, which will store this data in its Data property. It is this data that will appear

    in the DBGrid.While the client dataset will permit a user to change in the Data property, this data

    does not get sent back to the database server automatically. In order to cause any changesto be saved to the original database, it is necessary to make a call to the ApplyUpdates ofthe client dataset. In this simple application, this will be done when the user closes theformafter makingone ormorechanges.Toimplement thisbehavior, use the following steps:

    1. Select Form1 from the Object Inspectors combo box and set its Captionproperty to Simple Database Example.

    2. View the Events page of the Object Inspector and double-click the

    OnClose event to generate an OnClose event handler.3. Enter the following code into the generated event handler:

    if ClientDataSet1.ChangeCount > 0 then

    if MessageDlg('Save changes?', mtConfirmation,

    mbOkCancel,0) = mrOK then

    ClientDataSet1.ApplyUpdates(0);

    When the form is being closed, this code tests to see if the user has made anychanges to the data stored in the client dataset. If so, it asks the user if theywant to save the changes. If the user confirms, the changes are applied backto the database using ApplyUpdates.

    4. Select File | Save Project. Create a new folder called Simpledb in yourproject directory. Save unit1 using the name main.pas, and the projectusing the name Simpledb.

    5. Now click the Run button on Kylixs main form to run the application. Aftercompiling, the Database Login dialog box will be displayed. Enter the passwordmasterkey and click OK. When the form is displayed, it will look somethinglike that shown in Figure 6-10.

    6. Click the + button on the forms navigator control to insert a new record. In theCUST_NO field, enter 1016. Enter some data into each of the remaining fields.

    38 Kylix Developer's Guide

  • 8/7/2019 Kylix Databases Programming

    39/40

    7. Click the Close button on the forms title bar to close the form. This triggers the

    OnClose event. When the dialog box is displayed, click OK.

    Ill 6-6

    8. Run the project once more. Once the main form is running, select the recordthat you entered in step 6 and click the - button on the navigator control to

    delete the record. Again close the application and select OK when asked toconfirm saving the data.

    C h a p ter 6: O v e r v ie w o f Da ta b a se De v e l op m e n t

    Figure 6-10. The Simpledb project

  • 8/7/2019 Kylix Databases Programming

    40/40

    NOTE: The value of the CUST_NO field of the CUSTOMER table is automatically assigned by theemployee.gdb database. However, you are not permitted to post a change to a CUSTOMER recordwithout supplying a CUST_NO value. As a consequence, the value that you enter in CUST_NO may

    not be the value that ultimately gets assigned to that field. For example, if you repeat steps 5 and 6 of

    the preceding demonstration, entering a new record that reuses the deleted customer number 1016,the record that is eventually posted will use a new, unique custom number, such as 1017. This processby the database ensures that a particular customer number is assigned only once, and that once a par-ticular customer record hasbeen deleted, a deleted customers customer numberwill never be reused.

    You can find this code in the Simpledb project located in the simpledb subdirectoryat Osborne's Web site.

    Although this project was simple, it demonstrated how to do basic data access and useDBExpress components to permit a user to view and edit a table in a database. In the nextchapter you will learn how to use many of the properties and event handlers of the variousdata-aware components to customize the user interface of your database applications.

    40 Kylix Developer's Guide