SqueakSave

SqueakSave is an object-relational (O/R) mapping framework that provides the benefits of relational database storage without the need for extensive user defined mappings between object structures and relational schemas.
The API is kept as simple as possible and blends in seamlessly with Smalltalk programming paradigms. Only minimal configuration is required in order to add relational persistence to existing or newly created applications

Project Description

Programming with SqueakSave

Using the SqueakSave framework in order to add persistence to an application is intended to be as simple as possible. The only thing required to use the framework is the specification of valid connection data for accessing the underlying relational database. Once this has been done, all application objects can be saved with a simple call of the save method. But not only storing objects is meant to feel as natural as possible within a Smalltalk environment - and what feels more natural than telling an object to store itself? Retrieving objects from the database is also seamlessly integrated into the language because the query API closely emulates the Smalltalk collection protocol.

Extending SqueakSave

SqueakSave is, however, not only built with the goal of simple usage, but an emphasis has also been put on the extensibility of the framework. Therefore, abstract base classes exist that provide simple guidelines for the development of new ways to describe the mapping between objects and relational database schemas (no worries - they can still be auto-generated, only their appearance should change) or implement adapters for different relational database management systems

Outlook

The first iteration of the framework is currently under heavy usage by the students of a university lecture held at the Hasso Plattner Institute in Potsdam, Germany. All feedback that is gathered during those projects is recorded and will be incorporated into future versions of the framework. Additionally, we are also working on the extension of the framework with new features. This includes the ability to read or write O/R mapping descriptions of other O/R mapping frameworks like GLORP but also some improvements regarding caching mechanisms, eager loading, or accumulation of storage operations.

Developers & Acknowledgements

The framework has been developed by Thomas Kowark during the course of his master's thesis at the Hasso Plattner Institute (HPI) in Potsdam, Germany. Helpful advise has been contributed by the members of HPI's Software Architecture Group, especially Prof. Robert Hirschfeld and Dr. Michael Haupt. While the predominant part of the framework has been developed from scratch, the query mechanism is based on the work of W. Harford and E. Hochmeister for the ReServe project.

System Requirements

As the name implies, SqueakSave has been developed with and for the Squeak Smalltalk dialect. While porting the framework to other dialects and VMs should be possible without any major effort, we are currently not planning to do so because of the increased maintenance overhead the emerges with offering the framework and especially fixes for all available platforms.
With regards to Squeak, supported versions include 3.9 and 3.10 images. A good starting point for (web) development with Squeak are the development images built by Damien Cassou. They can be downloaded here

Download and Installation

Currently, the framework is only available from the SWA Squeak Source Monticello Repository:

The repository is set-up to be readable without any special permission, thus, username and password can be left blank. We are currently also working on combining all required parts into a package that can be conveniently downloaded with the SqueakMap Package Loader or through the Universe Browser. But as of now, the following packages have to be loaded in the following order:

First Steps: Adding Persistence to an Application

The following introduction will provide only a short description of the required steps to get your application up and running with SqueakSave. For a more detailed description please refer to the paper or the master's thesis about the framework. They contain much more detailed information about the usage and especially the inner-workings of the framework. A usage introduction is also available in the wiki of the SqueakSource Homepage of the project

In the following we will use a simple weblog application for our example. The application's object model is fairly simple:

Creating a configuration

SqueakSaves uses a naming convention based approach to determine the configuration for your application. This configuration basically tells the framework, where to store your objects. In order to create a configuration, all that has to be done is to create a subclass of SqsConfig that is named after the category of your application. If all you application's model classes for example reside in a category named MyBlog-Models then you can either name the configuration class MyBlogSqsConfig or MyBlogModelsSqsConfig. The latter, however, will only be valid for all model classes, so if you try to persist instances of classes in let's say MyBlog-ExtendedModels, the framework will trigger an error. No all that's left to do is creating a method named connectionSpecification on the class side of this configuration class. Depending on the chosen RDBMS driver, this method has to return an instance of the respective connection specification class. For PostgreSQL this method would look like this:

 MyAppSqsConfig class >> connectionSpecification
    ^ SqsPGConnectionSpecification
        user: 'test'
        password: 'test'
        database: 'my_blog'

Basic Persistence Operations

Now that the framework knows where to store your data, you can start to store created objects in the database and perform queries on the persistent space. Storing is as simple as it gets, since all you have to do is call save on any object of your application. All required table structures will be automatically generated, or, if already present, altered to reflect the current structure and data types of the saved object. So if you add an instance variable to one of your classes, the framework accordingly alters the table structure. So no need for you to write any O/R mapping descriptions by yourself - the framework takes care of this and you can alter them if you have to.
The following listing shows you in a nutshell what you can do with SqueakSave and your objects:

    author := Author new
        username: 'hemingway';
        password: 'secret';
        email: 'earnest@hemingway.net'.

    author blog: (Blog new
        title: 'My Blog'
    ).
    "this stores the author and the blog with one single call"
    author save.

    blogEntry := BlogEntry new
        title: 'My first Blog Entry';
        body: 'Just testing...'.

    blog blogEntries add: blogEntry.
    "saves the blog and the according blog Entry"
    blog save.

    "now we want to delete the blog entry from our database - was just a test, anyway"
    blogEntry destroy.

Searching

While simple storing is of course an important part of persistence, retrieving objects from persistent space is just as viable for any application. SqueakSave closely emulates the Smalltalk collection protocol, so you can almost write your queries as if you were operating on the collection of all instances of a class within your image. The following examples show some of the possibilities of the SqueakSave query mechanism:

    (SqsSearch for: Author) detect: [:anAuthor |
        anAuthor username = 'hemingway'].

    (SqsSearch for: Author) select: [:anAuthor |
        anAuthor blog blogEntries size > 10].

    (SqsSearch for: Blog) select: [:aBlog |
        aBlog blogEntries anySatisfy: [:aBlogEntry |
            aBlogEntry comments size > 1]].
As you can see, simple comparisons of direct attributes such as username with a given value are possible. Additionally, you can also follow multiple references from an instance variable and thus only select authors with a blog that has more than 10 entries or only blogs whose blog entries contain at least on with more than 1 comment. The only limitations of this algorithm are:

Summary

As the previous examples have shown, SqueakSave provides persistence for applications in a manner that can't hardly be simplified anymore. One save is enough to store an object and associated ones without caring about table structures, O/R mappings, and the like. Searching is also made as simple as possible and if it wasn't for the SqsSearch part, would be no different from searching for any object within the image itself. However, this functionality is only the tip of the iceberg, so please try the framework for your application and take a look at the detailed communication to explore the possiblities offered by SqueakSave.

License Information

The SqueakSave framework is licensed under the MIT License. The MySQL bindings that are available in the Monticello repository of SqueakSave are licensed under the GPL. However, they are not an integral part of the framework and distributed separately.