Introduction from Delphi in Depth: ClientDataSets
Before there was the ClientDataSet, Delphi's Borland Database Engine supported cached updates. When cached updates were enabled, changes to your database tables and editable queries were not written to the underlying database on a record-by-record basis. Instead, updates were delayed, permitting a group of changes to be applied to the underlying database in an all-or-none fashion (or even discarded altogether).
I wrote extensively about cached updates in the early days of Delphi, but over time cached updates lost their appeal. There were two reasons for this. First, the Borland Database Engine became dated, and it's SQL counterpart, the Borland SQL Links for Windows, was deprecated. The second is that cached updates became hopelessly broke, and this happened sometime around the release of Delphi 6.
Fortunately, there was a ready replacement — ClientDataSets. ClientDataSets supported all of the basic features of cached updates and much more. In addition to providing a mechanism for grouping updates, ClientDataSets also introduced in-memory management of data and indexes, the ability to persist data and restore it to its previous state, an intuitive interface for managing the cache, and a convenient mechanism for transferring a ClientDataSet's state between processes.
Originally ClientDataSets were only in the high-end versions of Delphi. Specifically, the Client/Server edition. Furthermore, the license to use a ClientDataSet in a distributed application was separate from Delphi, and was originally very expensive.
With the release of Kylix and subsequently Delphi 6 the ClientDataSet became available in the Professional version of Delphi, and the MIDAS (Multitier Distributed Application Services) license become affordable, and later was included with the product. (The technology that was MIDAS is now called DataSnap.)
With ClientDataSets now within reach of all Delphi developers, I became an enthusiastic advocate for their use. Not only did I speak extensively about the virtues of ClientDataSets at developer conferences, I also published an extended series of articles on the Borland Developer Network detailing the use and capabilities of ClientDataSets.
At a recent Delphi conference at which I was presenting a talk on advanced ClientDataSet features, I had a revealing discussion with an attendee. His questions about an issue he was having with ClientDataSets demonstrated a fundamental misunderstanding about how they worked.
When I explained what was happening, he expressed frustration that this information was not more readily available. I directed him to my previous articles and commented, in passing, that maybe I should write a book about ClientDataSets. "I'll be the first one in line to buy it if you write that book" was his reply.
This idea has been with me for some time, and this past winter I finally pulled myself together and started on this book in earnest.
Initially I thought that I could write this book by starting with some of my previous writings, including both the published series as well as a two-day Delphi course that I wrote and train called Mastering ClientDataSets. The trick, I reasoned, would be in the organization, and I had a lot of ideas about how I would go about this.
Projects like these tend to take on a life of their own, and once I was happy with the book's outline, I realized that I was committed to writing new material, a lot of new material. In the end, I estimate that at least 80 percent of this book is completely original, and that material that I salvaged from my previous writings often received extensive revision.
I am really happy about how this book turned out. I hope that you are too.
About this BookThis book takes an in-depth look at ClientDataSets. It begins with an overview of what a ClientDataSet is, and describes some of the ways that they can be used in your Delphi applications. It continues with a close examination of one of the more common uses for a ClientDataSet, reading and writing data from an underlying database through its interaction with a DataSetProvider.
Next you learn how to define the structure of a ClientDataSet, a process that can be undertaken both at design time as well as at runtime. The relative roles of FieldDefs and Fields are discussed, and the roles of persistent versus dynamic Fields are considered. How virtual Fields differ from data Fields is also explained.
Chapter 5 introduces indexes, including the difference between persistent and temporary indexes. The relationship between a ClientDataSet's indexes and those of an underlying database is also discussed.
In chapter 6 we take a long look at the change cache, the mechanism responsible for caching updates. Here you learn how to enable and disable the cache, how to detect changes to it, and how to modify the contents of the cache.
Chapters 7 through 9 introduce topics that will be familiar to many Delphi database developers, including how to edit, navigate, search, and filter data. These discussions, however, demonstrate the flexibility that ClientDataSets bring to these features, providing you with capabilities not available in other DataSets.
Chapters 10, 11, and 12 introduce some of the more interesting features found only in ClientDataSets. These features include aggregates, cloned cursors, and nested datasets.
The final three chapters of this book take a close look at DataSnap. These chapters specifically look at DataSnap applications where ClientDataSets in a client application interact with DataSetProviders running in a DataSnap server. Here you will learn to create DataSnap servers and clients using both the classic COM-based DataSnap as well as the new IP-based DataSnap first introduced in Delphi 2009.