Which Smalltalk?
smalltalkzen.wordpress.com
smalltalkzen.wordpress.com
However, choose your persistence carefully. The open-source Smalltalk landscape is littered with abandon-ware databases.
If you want an OODB, you can just save the image itself, use Magma (an open-source OODB, but its not very wel documented) or use Gemstone (through GLASS), which is commercial but well documented.
SQL support is weak if you want a nice ORM (like Rails' Active Record), and I've had success using CouchDB (a JSON document pretty much just maps straight to an object: keys -> values = instVars -> values).
I've been really happy with it, and its been reasonably fast in the Cog VM. I haven't explored using CouchDB's list views yet, but I'm considering that for just loading pre-built HTML for larger document lists.
A quick overview of Roe is at http://www.cincomsmalltalk.com/userblogs/avi/blogView?showCo... and the current source is at http://squeaksource.com/ROE.html . Note that ROE only supports PostgreSQL, but that's okay, because that's the only meaningfully supported SQL driver in Squeak/Pharo. Supporting other databases is actually quite easy in one front, but useless on another: I ported it to SQLite and MySQL around 2005, but never shared the changes, because MySQL simply cannot meaningfully optimize the queries generated by ROE, and SQLite at the time required a very unstable FFI wrapper that crashed the image constantly. If there's interest, I think I still have that code lying around somewhere.
I still develop in Pharo and deploy in Gemstone and I believe that scenario is not uncommon at all. It means my deployment is different from the one described in the post, I don't "clean-up" my image for deployment; I save my code changes to a monticello package, transfer it to the server through scp and load the package into Gemstone. Most of the time, I was able to just let the tools perform an auto-migrate on all existing instances.
Ruby feels closer to Smalltalk than Obj-C to me.
If you're familiar with Cocoa/Obj-C, you can have a look at http://www.fscript.org/
http://news.ycombinator.com/item?id=1887874
For me the key thing about Smalltalk is that its handling of abstraction scales well. On one hand, it's a modern, garbage collected, dynamic language in the same vein as Ruby, Python or Javascript. On the other, it give the programmer a lot more low-level control than any of those languages.
For example, Seaside makes heavy use of continuations. In most languages, you're at the mercy of the language designer as to whether continuations are supported: Ruby has them, but Python and Javascript don't. Smalltalk hasn't traditionally supported continuations, but it provides low-level control of the stack, and Seaside implements continuations as part of the framework.
Here's another, less exotic, example. Smalltalk provides GC-safe ways of manipulating raw chunks of memory, which other dynamic languages tend not to do. A couple of years ago, I needed to implement a specialized type of timestamp in Smalltalk. For my application, there would be many timestamps in memory at once, so optimized for memory usage. Internally each instance stored the number of seconds since March 1, 1980 as a 32-bit unsigned integer.
More recently, I implemented a timestamp object in Javascript. Without the level of control that Smalltalk allows, I ended up just wrapping Javascript Date objects. I don't know what the internal storage of Date objects looks like, but I bet it's more efficient than anything I could implement in Javascript.
You see this kind of thing all over the place in Smalltalk. Here's a comment I wrote a while back on syntax:
http://news.ycombinator.com/item?id=1289177
It's a bit hard to quantify, but I find this scalability of abstraction to be one of the key things I look for in a programming language. I'm not a Lisp hacker, but my impression is that this is one of the primary virtues of Lisp as well.
I haven't yet convinced Twitter to do a rewrite in Smalltalk ;). But it would be a step up from Ruby, even if only to get a better garbage collector.
How do they solve the apparent mismatch between Smalltalk philosophy of having everything in one image and the usual "files in directories" expected by version control?
Last time I used Smalltalk (a small project) I just kept the sources in files outside the image and reloaded from there but it felt clunky.
Pharo and Squeak Smalltalk have a DVCS client named Monticello that they use. It works similarly to Git/Mercurial/Bazaar/what-have-you, except that it versions classes and methods semantically instead of the actual changes file. This ends up working fine, and even has some major benefits (you can kiss whole swaths of problems goodbye when you're doing a semantic merge),but it does mean that your Smalltalk code requires its own version control. You can see a quick tutorial of how Monticello handles merging at http://www.lukas-renggli.ch/blog/monticello-merging , and there's what amounts to a command-line interface called Gofer you can read about at http://www.lukas-renggli.ch/blog/gofer . Most people I've seen just use the graphical interface though, which is documented (somewhat) at http://wiresong.ca/monticello/v1/docs/ .
VisualWorks Smalltalk has its own version control system, also semantic, but not distributed, called StORE. I haven't worked with it much, but the general idea is the same: version classes and methods rather than the changes file. I know it can at least import Monticello repositories as well, and possibly work with them natively, but I've never done that, so you'd have to do some more research.
Whenever smalltalk comes up I'm always surprised that I don't use it more often.
One small quibble: Pharo and Squeak's licensing are identical, so "clearer licensing" isn't a reason to choose one over the other. That said, Pharo is clearly a better choice for Seaside projects, since Pharo is the reference platform for Seaside.
Edit: In looking into the history, it seems the license has changed several times.
That said, unless you wear a tinfoil hat, I cannot imagine anyone seriously not using Pharo due to the above.