Smalltalk In Action

Explaining why Smalltalk developers like their images is a hard experience to convey to someone who’s accustomed to working with files. Here’s a video I found that shows what it is to work on a running program.

He’s demonstrating some of the features of the refactoring browser on a running instance of the classic Asteroids game. He extracts a method to a component, changes the color of the asteroids, then shows off undo and redo. He does so while the game is running without ever having to break his flow with something as silly as a compile, debug, run cycle that we’ve all grown so accustomed to in most other languages.

It doesn’t matter how fancy modern refactoring browsers get, as long as they’re still working on dead files instead of a live running program, they’ll never be able to compete with Smalltalk when it comes to developer productivity and maintaining flow.

Featured Resources

Whenever you look at a web design, you will notice that it’s usually not free from 3d animation effects. These features bring out the human interaction elements at its best. An affordable hosting will have you earn the desired outcomes from your website. There is a need of a good backup plan for your business hosting as the data security becomes a great concern in this case. And you will enjoy it’s advantages.

Related posts
    at: "Ajax: Using the Scriptaculous Updater in Seaside";
    at: "Page Templates and Seaside";
    at: "Rails vs Seaside";

9 July 2007 Upgrading Seaside

Here’s some very valuable info posted by Philippe Marschall (core Seaside developer) in the mailing list…

This is a short list of things to do when migrating for an older to a newer version of Seaside in the wiki at:
http://www.squeaksource.com/Seaside.html

2.6 to 2.7 must:

  • every component that uses the old default WAHtmlBuilder must do so explicity by returning it in #rendererClass
  • evaluate WADispatcher resetAll
  • use WATagBrush >> #title: instead of WATagBrush >> #tooltip:
  • move to new image map api, check all senders of #imageMap, see WAImageMapTag for details

2.6 to 2.7 should:

  • move to new header api, modify implementors of #updateRoot:
  • remove the implemtors of #rendererClass that return WARenderCanvas
  • migrate to WARenderCanvas
  • migrate from WAScriptLibrary and WAStyleLibrary to WAFileLibrary
  • use WAAnchorTag >> #with: instead of WAAnchorTag >> #text:
  • check for deprecated message sends
  • replace users of WAChangePassword, WAEditDialog, WAEmailConfirmation, WAGridDialog, WALoginDialog, WANoteDialog

2.7 to 2.8 must:

  • migrate to WARenderCanvas
  • backtrack state by implementing #states (check all senders of #registerObjectForBacktracking: and #registerForBacktracking)
  • move to new header api, modify #updateRoot:. #linkToStyle becomes #stylesheet #url, #linkToScript becomes #javascript #url:, check all implementors of #updateRoot:
  • use WAAnchorTag >> #with: instead of WAAnchorTag >> #text:
  • replace users of WAChangePassword, WAEditDialog, WAEmailConfirmation, WAGridDialog, WALoginDialog, WANoteDialog
  • every component that implements #initialize must send this message also to super (use SLint)
  • if you use Squeak 3.7 load SeasideSqueak37 after Seaside
  • if you use Squeak do not load into an image that has an earlier version of Seaside already loaded

2.7 to 2.8 should:

  • check for deprecated message sends
  • migrate from WAScriptLibrary and WAStyleLibrary to WAFileLibrary
  • remove the implementors of #rendererClass that return WAHtmlCanvas

I’m sure this list is not complete and I forgot stuff. So if you spot something that is missing send a message to me or the list or fix it directly. This is not on the Seaside homepage so anyone can edit it.
It will probably be moved to the homepage at a future point.

Cheers, Philippe

Related posts
    at: "Giles Screencast on Seaside and Rails";
    at: "07 December 2007 > Squeak Image Updated";
    at: "20 October 2007 > Squeak Image Updated";

On Simple Functional Idioms

I ran across an post by David Altenburg about the enumerate, map, filter, accumulate pattern. These are certainly common functional techniques, but they’re also common Smalltalk techniques. We call them do:, collect:, select:, and inject:into:.

He showed a Java implementation of a simple and common programming problem…

int maxSalary = 0;
for (Employee employee : employees) {
  if (Role.PROGRAMMER.equals(employee.getRole())) {
    int salary = employee.getSalary();
    if (salary > maxSalary) {
      maxSalary = salary;
    }
  }
}

Comparible to a C# 1.0 version…

int maxSalary = 0;
foreach(Employee employee in employees) {
    if(employee.Role == Role.PROGRAMMER
        && employee.Salary > maxSalary) {
        maxSalary = employee.Salary;
    }
}

Then he does a Scheme version using a more functional style…

(define (salary-of-highest-paid-programmer records)
  (accumulate
      max 0
        (map salary
          (filter programmer? records))))

And a Ruby version of similar style, note the Smalltalk’ishness of it…

employees.
  select {|emp| :programmer == emp.role }.
    map {|emp| emp.salary }.
      inject {|m, v| m > v ? m : v}

And for comparison here’s a Smalltalk version…

(employees
    select: [:emp | emp role = #programmer ]
    thenCollect: [:emp | emp salary ])
        inject: 0 into: [:a :b | a max: b ]

Though if I found the pattern that common I’d define a quick helper method on Collection to clean up the syntax to this…

employees
    select: [:emp | emp role = #programmer ]
    collect: [:emp | emp salary ]
    inject: 0 into: [:a :b | a max: b ]

What’s interesting about them to me is really the difference between the Java/C# approaches and the more composable Scheme/Ruby/Smalltalk style. Because Java/C# 1.0 lack first class functions (C# actually has them now in 2.0 and a nice lambda syntax in 3.0) and a literal syntax for declaring them, everything ends up being a special case of for/foreach. They lack the ability to factor out common patterns like select:, collect:, and inject:into: into higher order functions.

As a side effect, select: turns into nested if’s and a loop, collect: into a temporary variable and a loop, and inject:into: into both an if, a temporary variable, and a loop. You end up writing these patterns inline over and over rather than just reusing existing versions from the base library.

Languages that can’t support and make idiomatic the use of higher order functions, aren’t worth using these days in most domains. They’re just too damn much work. However, using functional techniques doesn’t at all mean using a functional language. All of these work quite well in good object oriented languages like Smalltalk and Ruby.

Related posts
    at: "Functional Programming in Smalltalk";
    at: "Lazy Initialization Smalltalk Style";
    at: "Seaside for the .Net Developer";

A Squeak Smalltalk Development Example

Stephan Wessels has put up a very large tutorial showing the complete test driven development of a game in Squeak. It covers quite a few things new Squeakers will want to know such as using SUnit to do test driven development, using Morphic to create Squeak widgets, using the debugger, and packaging the code with Monticello. It’s a great tutorial and I’m sure will become a popular resource.

However, despite the awesome effort (which I do appreciate), I have some problems with it. As with many other Squeak tutorials, it makes the mistake of using a standard Squeak image as you’d find on Squeak.org. This only helps further propagate the impression among newbies that Squeak is ugly, old fashioned, and lacking in all the features they expect from a more modern IDE. What you see in the screenshots is not a Squeak I’d use. Plain black code, ugly fonts, no intellisense, no use of the Refactoring Browser, no Shout Workspace.

Most developers who use Squeak would have a plethora of extra tools and utilities installed that make developing a much nicer experience than what you see in this tutorial. Do yourself a favor and start your Squeaking with a real developer’s image loaded with all the proper goodies like the SqueakDev image maintained by Damien Cassou.

Squeak.org still hasn’t figured out that its core audience should be developers, not children. They don’t seem to realize the base image they distribute actually scares away more people than it encourages to join the community. Though they do have a link to Damien’s SqueakDev image, they don’t encourage it like they do the base image, a mistake that leads new developers to open up Squeak for the first time, browser a tutorial or two, and toss it aside as a silly toy, never having seen the real power or beauty that is Smalltalk.

So all you developers out there using Squeak, please, stop showing people ugly images. Marketing matters, looks matter, and that stuff scares people away. Load up some decent fonts, setup the minimum *required* goodies like Shout, the Refactoring Browser, and ECompletion. And if you aren’t using these goodies, you should be, and you shouldn’t be making tutorials without them because it gives people a false impression of what Squeak is. Squeak is an awesome development environment that sadly doesn’t come out of the box that way, you have to start with the right box or learn to build your own.

Squeak.org could learn a lot about marketing Squeak by looking at how rubyonrails.org markets Rails. If there’s one thing Ruby does vastly better than Smalltalk, it’s marketing. Smalltalk continues to languish not because of technical merits, but because of bad marketing. Beaten by Java, and now beaten by Ruby, by marketing alone.

Related posts
    at: "Seaside 2.8 Released";
    at: "Better Web Application Development, a Comparison of Frameworks";
    at: "22 February 2007 > Squeak Image Updated";

« Previous PageNext Page »