REALbasic Tricks: Shell and cURLby Jacek Artymiak
Although the developers of Rapid Application Development (RAD) tools have always promised "power with ease," I must admit that my own experiences with these integrated development environments have not been as satisfying as they were supposed to be based on the marketing hype. They're fine for building an application's GUI, and adding some simple logic, but as soon as I needed to do something more complex, something that would take only a few lines of shell or Perl code, I had to write those pesky XCMD extensions in raw C/C++. The additional testing I had to do meant that whole development process was anything but "rapid."
That's why I like open source software, which offers all the power you can handle and none of the visual fluff. For the visual GUI there's always Tk and you're basically set. However, there are times when open source tools just cannot help us. At times like these REALbasic has been very helpful for both Mac and Windows development. I've always liked it, but I did not really like writing XCMDs every time I was going beyond what REAL Software developers had built into it.
Best of Two Worlds: REALbasic and BSD
All this changed when Apple introduced Mac OS X, which comes with a full BSD system hidden under that cool Aqua GUI. Those who need it can access all standard UNIX commands, shells, Perl, Tcl, and all other goodies which UNIX users and developer take for granted.
"Wouldn't it be nice," I thought to myself, "if I could mix the best of REALbasic and BSD in my applications, call on the power of the underlying BSD system while hiding the gory details from the user's view?" One way to do it is through the AppleScript interface to the Terminal application, but that's not the only way. Another way, and one which I like a lot, is through the REALbasic Shell class. Until now the Shell class and other ways of executing external code offered a limited number of possibilities, because there was not much to call, really.
Now with Mac OS X we can call any system command or a supplied script and capture its output. Sending text back and forth may not seem like a lot, but it is a very powerful mechanism that can nicely supplement whatever it is that you need and cannot find in REALbasic. It's also a nice way to add Aqua GUI to your favorite collection of scripts.
Suppose you want to write an application that needs to download files from some location on the Web and processes them to do its job. You could write your own implementation of the HTTP or the FTP protocols, use somebody else's code, or use Shell and let curl do its job. (For more information on curl start the Terminal application, type man curl, hit the Enter key and read the curl manual, Space is forward, b is backward, and q quits the manual.)
Building an Actual Application
To see how such application could be built in practice, we will start with a simple GUI front end to curl. It will be a good illustration of the basic principles and can be later expanded and modified to suit your needs.
To use Shell, you will need to do the following things:
Start a new project in REALbasic (if you don't have it, you can download a 30-day demo).
Create a simple user interface like the one shown in Figure 1 below.
Change the Name property of the upper text field to SourceField. Also check the Multiline and ScrollBarHorizontal properties.
Change the Name property of the lower text field to URLField. Change the Name property of the button to GetPage and check the Default property.
Add a new module with File -> New Module. Double-click on the Module1 and press Alt-Apple-P to add a new property.
Type 'page as Shell' (without quotes).
Uncheck Private and click on the OK button.
Double click on your application window and add the following block of code in the
Double-click on the Get Page button and add the following block of code in the
If TargetCarbon then page.execute "curl -LsS " + URLField.text If page.errorCode=0 then SourceField.text=page.result else SourceField.text="" MsgBox "Could not retrieve " + URLField.text + chr(13)+"Error Code: " + Str(page.errorCode) + chr(13) + page.result End if End if
Save your project under the chosen name.
Press Apple-R to run it.
Type the URL of the page you wish to download.
Click on the Get page button (or just hit the Enter key).
If all goes well you should see the source of the page you requested in the upper text field (see Figure 2). When curl reports errors, you will see the message box telling you that the given URL could not be retrieved (see Figure 3). You could even write a much better handler for errors and expand our little application into something more useful.
There is one small disadvantage to using REALbasic and Shell in this way: such code in not portable to Microsoft Windows simply because Windows does not come with a BSD system underneath its GUI. That can be solved quite easily by installing Cygwin, but that solution can no longer be called elegant.
You can download the source code of this application here.
Jacek Artymiak started his adventure with computers in 1986 with Sinclair ZX Spectrum. He's been using various commercial and Open Source Unix systems since 1991. Today, Jacek runs devGuide.net, writes and teaches about Open Source software and security, and tries to make things happen.
Return to the Mac DevCenter.