Acceptably Nonterrible Revision Control for Mathematica

by Danielle Fong

I discovered today, to my amazement and horror, that the otherwise exceptionally advanced and useful Mathematica 7 has only a single level of undo in its notebooks. And no redo.

Furthermore, the lone autosave feature, hidden deep, is triggered upon every cell evaluation. Every time you evaluate something in a notebook, it will save the file – overwriting the last version.

I spent an hour looking to see what was the matter. I was convinced that it must be my own obtuseness causing me not the find or see or properly use the actual undo function there present. Instead, I found several newgroup threads in which people exclaim their amazement that such vital features as multiple undo and revision control hadn’t made it in, and apologists of various employ, Wolframites and others, who wrote back about the academic difficulty inherent in making multi-level notebook undos for notebooks fed with dynamic data.

I’ve got news for you Wolfram Research. It doesn’t matter. What people care about is their input data. What people don’t want about is destroyed work – the product of their labor, channeled through from their mind and out through their fingers, typed into little, nicely formatted cells. Almost everything else can be reconstructed from that input. The cases in which the inability of a simple multilevel undo to capture changes in dynamic data could possibly destroy work make up a fraction of a percent. Catastrophic hard disk failure is more likely.

I checked for a while to see if anyone found a solution more advanced than to manually save often, and use standard revision control. I couldn’t find anything.

Thus, I present my complete hack of a solution. It seems to work acceptably well — as in, I think I can rely on it to save my work, most of the time, if it really came down to it. But use at your own risk:

1. Get Dropbox. ( This is a file sharing and revision control system that’s built right into the operating system, Windows, Mac OS X, Linux. One creates a folder, shares it over Dropbox, and every file in it is mirrored, automatically, on their servers. In particular, they keep track of revisions: so far as I can tell, every saved file is queued to be uploaded.

2. Enable Autosave. One can set this for the current notebook by evaluating the following line: SetOptions[SelectedNotebook[], NotebookAutoSave -> True]. This setting persists across saves.

3. Now every time one evaluates a cell, the notebook is saved. Further, while the file is apparently overwritten locally, the revision history (which I believe is, in most cases in full,) has been uploaded to Dropbox, or queued by the client.

4. To recover a revision, one can check the revision history in the Dropbox web interface.

5. Standard diff facilities are less useful, because the notebook files are highly structured. However, there’s a structured diff built into Mathematica, Notebook Diff in the AuthorTools package. One loads the package by evaluating << AuthorTools`. One can run this command NotebookDiff[nb1,nb2], where nb1 and nb2 are either notebook objects or their filenames with full paths.

This seems to work well enough for now. In the meantime, Wolfram Research, get your act together! You are driving people crazy.

I am also putting together a way to use the Units` package throughout (much more of) Mathematica, in particular, in conditionals and numerical functions. In practical engineering it could often be said that converting units is one’s primary occupation. For this reason the units package came to me with extreme promise. Built into the algebra package as it was, it could be used, in an extremely simple way, to check dimensional and unit consistency. However, it is not natively compatible with numerical functions: one cannot plot expressions including units, or expect results from comparison operators, and they can’t be used with functions like Max and Abs, or within the solver for numerical differential equations. It would be so wonderful if it could. I think I’ve figured out a way forward there, but we’ll see. The basic idea is to set to 1 all base units in a particular unit system — SI or CGS. This is likely to work for mechanics, however due to the differences in how the CGS and SI systems define electromagnetic quantities, making it work well for electromechanics is either a subtle project, or a doomed one. [Edit: David Park’s ExtendUnits package appears to do exactly this. It’s $30, though.

Also, I don’t know if anyone’s really following this, but we’re not working on vehicles specifically anymore; LightSail is directing itself towards energy storage as a first product. Our website is woefully out of date. Vehicles or vehicle systems may be a further product and direction of ours, but by focusing on energy storage we can really prove out the core technology without the additional hassles of becoming an automotive company.