Saturday, April 29, 2006

Rur-ple 0.9.7a: bug fix

Once again, rur-ple was broken on Linux (and Mac OS); however, this time the bug was reported (only the second ever reported bug through sourceforge since Stas Z guided me to make it work on Linux for the first time!). It is now fixed :-)

There must be some other bugs, somewhere... After all, I did not use any kind of "unit tests" for most of the code. Anyone that tries to use rur-ple and find problems should feel free to report them!

As soon as I can get about a week's worth of time (and inspiration!) to write the last lessons, I will be able to finally release version 1.0. After that, watch for a new version that will use a web browser (instead of wxPython) as its graphical environment. Now, what I need is a new name for that future version...

CherryPy is great!

Inspired by Ian Bicking's HTConsole, I wanted to see if I could get a simple "Python compiler", similar to Lightning Compiler but using a browser window instead of basing it on wxPython. Having no experience with any web programming, and looking at Ian's code, I thought it would take me forever to get this going. Also, I didn't really want to have to learn about all the packages used by Ian to produce HTConsole.

After a few simple attempts with Python's webbrowser module, a fruitless query on comp.lang.python, and some wandering on the web, I came accross CherryPy. To be honest, I had heard of CherryPy before, but had never looked at it as I thought it was something I would never need.

Lo and behold, simply after reading the basic tutorials included with CherryPy, I was able to write a very small program which does pretty much the same thing that earlier versions of Lightning Compiler could do. The complete code is included below:

import cherrypy
import os
from tempfile import gettempdir
TMP_DIR = gettempdir()

class PythonRunner(object):
title = 'Play with Python'

def header(self):
return '''
<html>
<head>
<title>%s</title>
</head>
<body>
<h2>%s</h2>
''' % (self.title, self.title)

def footer(self):
return '''
</body>
</html>
'''

def index(self, code=None):
cherrypy.session['code'] = code
output = ''
if code is None:
cherrypy.session['output'] = ''
else:
tmp_filename = os.path.join(TMP_DIR, 'my_file.dat')
f = open(tmp_filename, 'w')
f.write(code)
f.close()
f_in, f_out = os.popen4("python %s"%tmp_filename)
output = "The result of"
output += "<pre><font color='blue'>%s</font></pre>is: "%code
output += "<pre><font color='green'>"
for line in f_out.readlines():
output += line
output += "</font></pre>"
cherrypy.session['output'] = output
return self.header()+'''
Type in your Python code.
<form action="index" method="GET">
<textarea name="code" rows=5 cols=80></textarea><br/>
<input type="submit" value="Run Python"/>
</form>
<br/>
%s
''' % output + self.footer()
index.exposed = True

cherrypy.root = PythonRunner()
cherrypy.config.update({'session_filter.on': True})

if __name__ == '__main__':
cherrypy.config.update(file = 'tutorial.conf')
cherrypy.server.start()
And here's what it looks like (html code simply pasted below; it doesn't work here!)

Play with Python



Type in your Python code.





The result of
def hello():
print 'Hello from CherryPy!'
hello()
a = 3
print a*3
is:
Hello from CherryPy!
9


Thank you CherryPy developpers!

Thursday, April 27, 2006

Lightning 2.0

I've upgraded Lightning Compiler significantly. It is now possible to have more than one editing tab. It is now also possible to run doctest suites, with an external file. As usual, it can be found on sourceforge.

Lightning Compiler (LC) is a wxPython based app. LC's purpose is to provide a friendlier environment to tests Python code snippets than the Python interpreter. It does include an interpreter (pyShell) but it is most likely to be used for its editor. You can execute the code that appears in the editing window and the output is redirected to an output window. raw_input() and input() are handled via dialogs. The basic layout (output window to the side or below the editor window) is customisable.

LC comes in a zip file with a sample app, showing how it can be embedded in other applications, as well as a sample script with doctests and a text file containing additional doctest based tests.

Since LC uses wxPython, it can not be run with a basic Python installation. If there is some interest, I might try and adapt it so that it could use Tkinter instead (as an option. However, I have no experience with Tkinter. Any help would, of course, be appreciated :-)

Sunday, April 23, 2006

Lightning Compiler with doctest support

As readers of this blog will know, I wrote "Lightning Compiler" (LC) as a small application to test code snippets. Inspired by an idea from Jeffrey Elkner, I added two new options for LC. It is not possible to press a button an execute a code snippet as though it was imported as a module by doctest, either in "normal" mode, or in verbose mode. For example, suppose I have the following code:
def hello():
""">>> hello()
Hello!
"""
print "Hello!"
I can simply press LC's "docTest" button or "verbose" button to run Python with doctest.

What's happening behind the scene is that the following two lines
import doctest
doctest.testmod()
are appended to the code in the window, all of which is saved to a file which is then executed by Python, with or without the "-v" option. The result is saved to a second file which is then displayed in LC's output window.

Granted, if your script already includes some doctest-based testing within a "standard"
if __name__ == "__main__:"
block, this addition to LC may not seem that useful; however, if you already use the "if..." block for something other than tests with doctest and have some docstrings-based tests in your code, it might be worth your while trying LC's new feature.

Thursday, April 13, 2006

Thoughts on the Shuttleworth Summit

Guido and Kirby Urner are two of the 20 or so participants currently taking part in the Shuttleworth Summit. To put it simply, the objective of that summit is to find a curriculum that will fit mathematics, where a child will have mathematical tools to solve problems, and to acquire their analytical skills, and while making efficient use of technological tools. During the discussion, it has been suggested that a possible way might be to start kids with Logo, then maybe move on to Squeak, then Python. I would argue that a programming environment like rur-ple might be more suitable and sufficient to replace both Logo and Squeak, while being used to introduce Python. Many of my thoughts on this have been influenced by a paper on mini-languages. (I encourage everyone to read this paper.) I should also acknowledge that the basic idea behind rur-ple is not my own, but rather Richard Pattis with his "Karel the Robot", which is mentioned in that paper.

I am going to present an admittedly one-sided view in order to invite some discussion. The reality is that Logo and Squeak have been used very successfully with learner of all ages - something I will conveniently ignore in my argumentation! Furthermore, because I want to use this post to try and provide some feedback to Kirby that he can perhaps use while he is at the summit, the depth of some of the arguments presented will definitely be less than satisfactory.

Let me jump straight into the discussion by first arguing Logo might be too complicated as a first step, for at least two reasons. In decreasing order of importance, they are: 1. Advanced geometry; 2. Too many (complicated) commands. Furthermore, I would argue that Logo is limited in its ability to introduce problems requiring analytical skills.

First, Logo (and similar turtle graphics environment) uses general two-dimensional motion. The mathematical concepts that are needed/introduced include length and angles (measured in degrees). While integer values are used, units of length are too small to be easily measurable on the screen. By contrast, rur-ple uses restricted two-dimensional motion, as combinations of either vertical or horizontal motions. The basic stepsize is easily measurable on the screen. While rur-ple is designed to introduced coordinates (which are, arguably, a fairly advanced mathematical concept), programs can be written without making any reference to this concept. Furthermore, even without writing an actual program, one can guide the robot, making it move and turn by using the keyboard; this can be useful in visually determining the order in which instructions must be written.

Note that, in a future version of rur-ple (after I complete version 1.0) will include a second environment which will be essentially a "turtle graphics" environment, like that of Logo.

Second, Logo generally include the following commands (written in non-abbreviated form): forward #, backward #, right #, left #, pen_up, pen_down, restart (cs), as well as a repeat instruction. Note that the symbol "#" refers to a numerical variable. By contrast, rur-ple's basic commands are: move(), turn_left(), pick_beeper(), put_beeper(), and turn_off(). Rur-ple also includes a repeat() instruction. One can easily make a correspondance between Logo and rur-ple's commands and see that Logo includes two extra commands (backward and right) that can be emulated by appropriate combinations of other commands. Granted, the previous argument is a bit weak... However, note that 4 of Logo's basic commands require the use of an additional numerical arguments. This may seem trivial ... but for an absolute beginner, such a combination, like "forward 5" is an advanced concept as compared with a simple instruction like move(). While it is currently not designed this way, rur-ple could (and probably should) be easily modified so that the basic instruction move() could take an optional argument, like move(5), which would more closely match Logo's syntax. This is most likely how the future "turtle" environment for rur-ple will be designed.

Another conceptual hurdle present with Logo is the concept of "pen_up" and "pen_down". Again, for the readers of this blog, it probably seems very simple. However, I understand that this is something that has to be explained to learners (especially the younger ones), as it does not have an immediate analogy in their experience. I would argue that a more natural set of commands would be something like "start_drawing()" and "stop_drawing()". This could then later be expanded to something like "start_drawing(color=red)" and "start_drawing(color=red, thickness=2)". Another future expansion of rur-ple would be in a third environment, this time a 3-dimensional one (perhaps using Vpython).

I have mentioned that Logo is perhaps too limited in its ability to introduce problems requiring analytical skills. This is because Logo's traditional environment is an empty one. By contrast, rur-ple introduce a world in which obstacles (walls) can be present. One can then ask the user to solve various programs, from a simple "climbing a step" to finding a way out of a maze. This is done by introducing, one keyword at a time, Python's syntax. In fact, because the full power of Python is available, one can even easily use rur-ple to program a visual solution to the Tower of Hanoi problem!

This brings me to my final, and perhaps most important point. If one is to design a curriculum making use of technological tools to introduce mathematical and analytical skills, the focus should be on coming up with a coherent and progressive set of problems to be given to the students. The main idea should be to use the technological tools to solve the problems and learn about them, rather than using the problems to learn about the technological tools. I have to admit that rur-ple's lessons so far have been written in the second way: problems are introduced as a motivation to learn about computer programming (i.e. a technological tool). Perhaps the result of the Shuttleworth Summit will influence future lessons that will be included with rur-ple!