Pharo: Tips and Tricks

Hi guys. It is going to be 4 years since I have started to develop with Squeak/Pharo. In the last months, talking with people or by reading the mailing list, I noticed that I may know some tricks and tips of Pharo that not everybody know. If you are an advanced Pharaoer, you probably won’t learn anything new but, if you are a beginner or so, this post may help you.

I have structured this post so it can be easy to follow. There are different categories and, for each of them, there are several tricks. Each trick has a detailed name so you can quickly scan them and only read those you are interested in.

UPDATE: James Robertson has started creating videos for some of the tips I mention here. So for those that there are already videos, I will paste the link. Thanks James!


“Method source with it”: Have you ever needed to search a string in EVERY place of an image? I mean… in methods’ source code, class comments, etc. I need this all the time. To do this in Pharo, type what you want to search, select that text -> right-click -> extended search -> method source with it.  Notice that you can type whatever you want. For example, you can search ‘text’ (with the quotes included) or #whatever. Whatever you type will be literally searched. You can also see the other options under “Extended search” because they are also useful. Video here.

Spotlight: This is a new tool in Pharo 2.0 similar to Mac’s spotlight. For those of you who miss Algernon (like me), this is what you are looking for. Stop writing classes/method in code panes, workspaces or whatever just to browse them. Typing in code panes sucks because then you have to remove it or discard it. Opening a workspace takes too much time and then you end up full of windows. So… to try it, just SHIFT+ENTER and the input will appear in the right top corner of the image. The text inputs work exactly as the code completion (so it works for classes and methods). It has the same behavior as if you were typing in a workspace. Once you have selected something from the list, just enter to open a browser with it. Video here.

Finder examples: Sometimes I have some receiver object and I know what answer I want to get but I don’t remember which is the message. For example, last week I wanted to know which was the method to remove the prefix from a filename. So, open the Finder and, in the list of options, select “Examples”. Then, in the input pane, write ‘whatever.fuel’.’whatever’ and hit search. Wow! Pharo told me the method I was looking for is #withoutPeriodSuffix. For more details about this tool, print ‘FinderUI methodFinderExplanation’. AWESOME, isn’t it? Now, being serious, the idea is nice but the implementation…mmmm. Just check method MethodFinder class >> #initialize2. Of course you cannot try all selectors of the image because there can be lots of bad problems. However, having all the selectors hardcoded in a method is not nice either. Video here.


How to script them? It usually happens that you need to set your own settings from code (and not from the Settings Browser). For example, when setting them with StartupLoader. But how do you know for each setting how to do it by code? Easy. Open Setting Browser -> go to the setting you want -> right-click -> Browse. Or, you can just use the shortcut of browsing (CMD+B in Mac). This will open the method that declares the setting and has the pragma. In such method, you can search the setting you were looking for and you will find the selector and class that set/get the value of the setting. Video here.

StartupLoader: Wanna run scripts from startup with Pharo? See my previous post!

Changing logo, desktop, theme and friends: Did you know you can change all of them? You can build your own images that look completely different from the default one. Example:

PolymorphSystemSettings setDesktopLogoWith:  (ImageMorph withForm: (ImageReadWriter formFromFileNamed: '/Users/mariano/PhD/Marea/Fuel/fuel kit logos/logo-fuel-header-title.png')).
PolymorphSystemSettings desktopImageFileName: '/Users/mariano/PhD/Marea/Fuel/fotos/1997_Need_For_Speed_2_Special_Edition.jpg'.
UIThemeW2K beCurrent.

Gives this ugly image:

System fonts: Sometimes you don’t like the fonts that come out of the box with Pharo. In other cases, if you have non UTF characters, then you may be forced to use a different font. To do that, you have to use “Free Type”. Go to the Settings Browser -> type “font” in the search -> check the item “Use Free type…”. Now, you can click on each of the standard fonts and a pop-up will appear and show you all the fonts available from your OS. Notice that if you make the code font too big, bringing up tools will slow to a crawl. Anyway, here is a crazy example:

Facing problems

Copy the stacktrace from a debugger to clipboard: There are lots of time when I just want to paste the stacktrace of a debugger to clipboard. One way is to go and see the PharoDebug.log. Problem is that since I use new images all the time, I always need to print “Smalltalk imagePath”, then go there and open the file. So… if you are in a debugger, you can do right-click -> Copy to clipboard and that’s all 🙂  Video here.

Interrupt key: Sometimes your image goes into an infinitive loop or something similar and you want to interrupt what it is doing. To do that, you can press the interrupt shortcut and it will try to interrupt the processes and open a debugger. For more details, read the Pharo book.

Send kill signal: If your image “hangs” and you are lucky, the interruption key will help you. If you are not, then you have a different way to know what was happening. You can KILL the VM by sending a special signal and the VM will print the Smalltalk stacktrace of the current processes in the OS console (stdout) or in a .dump file (located in the image path). This is a good last resort when nothing else is working. For this trick, you have to be using latest Cog VM since it is quite new I think. Example:

kill -s SIGUSR1 4943

Where 4943 is the PID of the VM you want to kill.

Recovering lost code: Probably, one of the things Smalltalkers are always proud of saying is “In Smalltalk you never lose code” hehhehe. So… your vm crashed and you didn’t save your code? Well, there are different ways of recovering the code.

1) Tools -> Recover lost changes. There you can select the date from where to start watching the changes. Once you select a point in time, you can go item by item seeing what you want to recover. What I usually do is multi-select all the ones I want to recover and then I click on “file in selections”. That will install back those lost changes. Notice that this is thanks to the .changes file so you need it in order to recover changes. Also notice that even Do-Its are saved.

2) If your image does not even start, are you screwed up? No! You can even browse the changes and recover your lost data in ANOTHER image. Just open another image and then drag and drop the .changes of the image you lost the data. Then repeat the option 1).

3) You can always take your prefer text editor, open the .changes file and copy paste 😉

Video here.

System reporter: This is a small tool that gives you information about the image, VM and OS you are running. This is also very useful when you want to report an issue. To access it, System -> System Reporter. Video here.


History to view changes: I don’t feel proud of discovering this functionality just quite recently hahahah. In several opportunities, I load version XXX (or nothing) of a package and I want to see the differences between YYY and ZZZ. I knew the “Changes” option from Monticello but that compares a version of the repository to your installed version. So, I always needed to load the oldest version of the one I wanted to compare (YYY in this case) and then select ZZZ and do the “Changes”. That sucks because of the time it takes but also because I need to load a different version (maybe I have changes in local version). So…. to do this, open a repository, select the version you want (ZZZ in this case), press the button “History” and, in the pop-up, choose which version you wanna compare to. Then, right-click -> view changes -> MyPackage.mariano.42. Video here.

Global package-cache: The package-cache is created by default as a subdirectory where the image is. For me, this is totally useless since the package-cache should be global, that is, shared between all your images. Therefore, I recommend you to change the directory of the package-cache. You can even do it in your startup preferences as I do:

| sharedPackageCacheDirectory |
sharedPackageCacheDirectory := (FileDirectory on: '/Users/mariano/Pharo/localRepo/')
MCCacheRepository default directory: sharedPackageCacheDirectory.

Notice that depending on the amunt of mcz files, you may notice a slowdown when using Monticello Browser. A couple of things have been done in Pharo 2 regarding this problem but it is not completly solved yet.

But you don’t want to start with an empty package-cache when you already have lots of .mcz around your machine, do you? So, you can run this small script:

find /Users/mariano/ -name "*.mcz" -print0 | xargs -0 -I {} cp {} /Users/mariano/Pharo/localRepo/

Video here.

Setting your username and password: If you have a project which does not allow global commit access and you use Metacello, then you will understand my problem. You downloaded your project, you change something and, when you are going to commit, you get a nice error saying that you don’t have access grrr. Then you open the Monticello repo description and you notice that this is obvious because you didn’t put your username and password. Metacello allows us to put that in the ConfigurationOfYourProject but you may not want to put it there if this is public. Therefore, I did a script (also attached to my startup preferences) that fixes this for me. It is a hack but here it is:

(MCRepositoryGroup default  repositories
select: [:each | (each isKindOf: MCHttpRepository)
and: [((each locationWithTrailingSlash includesSubString: '')
or: [each locationWithTrailingSlash includesSubString: ''])]
]) do: [:each |
user: 'MMP';
password: ((FileDirectory default oldFileNamed: '/Users/mariano/Pharo/repositoriesPassword.txt') contents).

I guess the code is self-explanatory.

Random useful options: There are a couple of useful operations with Monticello. To revert your local version to another one, right button on a package -> revert package -> choose version. To copy a version of a package from one repo to another one, select the version -> button copy -> select target repo. Do you already have a repository and you want to add it to another different package? Adding again the repo is boring… right-click the repo -> add to package -> select package.


There is a top-right arrow!: Maybe you never saw this arrow before but open, for example, a workspace and you will see that, in the top-right of the window, there is an arrow. You can click on it and a menu with options will appear. This menu depends on the window/tool so you should go window by window and discover new stuff 🙂 Video here.

Recover text from closed workspaces: If you closed a workspace and you had something useful there, you can still recover it. Click on the top-right arrow (as described in the previous item) -> previous contents -> select the piece of text you want to recover 🙂  Video here.

Halt once: Sometimes you want to debug a code and you want to halt in a method. However, the method can be complicated and can be sent lots of time. You can even hang your image. This is typical when debugging with Morphic. To achieve this, we have a #haltOnce. You use it in the same was as #halt with the only difference that you have to tell the system to start taking into account such halt. To activate that, go to System -> Enable halt/inspect once.  Then, it will just halt only once. Of course you can do it by code (Halt enableHaltOnce and Halt disableHaltOnce). Another useful message is #halfIf: [xxx] which is easier than xxx ifTrue: [self halt]. Video here.

Writing to stout and reading form stdin:  Writing to stdout is really easy:

FileStream stdout lf; nextPutAll: 'zaraza'; lf.

Reading from stdin is also easy but I recommend you to read this thread. Video here.

Shortcut explanation for beginners: Do you know that when you see in a menu a shortcut between parenthesis, like (o) (which is lowercase), it means cmd+o. But, if it is (O), it is cmd+shift+o hahahah. Quite mysterious the first time 😉

Creating your own shortcuts: Did you know you can create your own shortcuts? And, what’s more, that there are already lots of shortcuts for global actions like opening a transcript, a workspace, Monticello, etc, etc, etc. For more details, check the Keymapping project.

Why GC is not collecting a particular object?: Sometimes you want to understand why the GC is not removing certain object. Pharo let us explore the pointers to a particular object meaning we can trace the references and therefore understand who is referring to the object. To do this, explore your object ->right-click -> explore pointers. Or, by code, “yourObject pointersTo”. Video here.

Debugging with closures and loops: When you are debugging, sometimes you need to step into a closure. this happens, for example, when you are iterating/filtering/whatever a collection. In those cases, you have to use the “Through” button of the debugger.

Cleaning the system: “ScriptLoader new cleanUpForRelease” generates a really clean image. You can see that method to understand what it does. The resulting image is much smaller than the original one. You also have “ScriptLoader new cleanUpForProduction” which not only cleans, but also removes some stuff (like tests). That image is very small and useful for deploying applications. Video here.

How to turn on Halo’s?  Contrary to what people think, Halos are present in Pharo but only when you really want them 😉 In Mac, by pressing Apple-Shift-Click and, in Linux/Windows, by pressing Shift-Alt-Click. In Pharo 2.0 the two-way cycling (i.e. the way it was in Squeak) can be restored via “Morph cycleHalosBothDirections: true.”.  Video here.


Enable and disable plugins: Nautilus provides several plugins and, of course, you can build your own. To see the available list of plugins and add or remove them,  click in the top right arrow of a Nautilus browser -> Nautilus Plugin Manager. There, you can add and remove plugins with absolute freedom.

Get list of available shortcuts: Nautilus can show you the list of available shortcuts. To do that, click in the top right arrow of a Nautilus browser -> Shortcuts descriptions. You can then select from the list which group of shortcuts you want to see. Video here.


So I hope that you could learn at least ONE trick! If you didn’t, I am sorry. You should tell me new tricks 🙂  If you did learn something, then excellent. Do you have more tricks to share with me?  There are some tricks in the Pharo collaborative book.

See you soon!

16 thoughts on “Pharo: Tips and Tricks

  1. That’s a neat trick with the global package-cache. I’ve never needed it because I put all my images in the same directory, so “./package-cache/” just happens to always point to the same directory…

  2. Great post, Mariano! A few things that stood out:
    * the “kill…” is pretty cool. I didn’t know about that one. Looks like a good last resort when nothing else is working
    * Compare arbitrary Monticello versions – cool!
    * “find…” – great functionality, but getting away from that sort of thing is why I learned Smalltalk 🙂 It’d be great to do it via FS…

    And a few additions:
    * the Spotlight shortcut (on Mac at Least) is Shift+Enter
    * In the Settings browser, you can also bring up the method with the “browse” shortcut (Cmd+B on Mac)
    * Fonts – if you make the code font too big, bringing up tools will slow to a crawl

    Re the shared package cache, I noticed a discussion on the dev list about a big slowdown for large caches. Has this been fixed?

    Sean (DeNigris)

    1. Hi Sean. Thanks for your remarks, I have updated the post. I didn’t understand the

      “* “find…” – great functionality, but getting away from that sort of thing is why I learned Smalltalk 🙂 It’d be great to do it via FS…”

      Regarding the pacakge-cache and the slowdown to Monticello, a couple of things have been done in Pharo 2.0 regarding this problem but it is not completly solved yet 🙁

      1. Re “find”, I meant ‘find /Users/mariano/ -name “*.mcz” -print0…’. It’d be nice to do that in Smalltalk

  3. Just another example of using the Finder > Example since this is a great tool that I didn’t learn how to use for a long time. I have just now again been pleasantly surprised and mildly amazed that it works a well as it does.

    I am creating a mouse-over popup using Rossal, for which I needed to format a string to a maximum width. This is something I thought likely already done within the standard image but before rushing to the mail list to ask an old-hand where I might find it, I thought I’d just try…
    1. World Menu > Tools > Finder
    2. Choosing “Examples” from the pull down menu.
    3. In the search-input-field typing: ‘abcdef’ . 3 . ‘abc’, String cr , ‘def’
    4. Clicking the button.

    which gave me one result String>>withNoLineLongerThan:
    that was exactly what I needed.

    You will notice that the search input field is an array of three items:
    * ‘abcdef’ – this first item is the receiver of the message
    * 3 – middle items are parameters to the message
    * ‘abc’, String cr , ‘def’ – the last item is the message-return-value

    The really cool part of this is being able to construct the message-return-value as an expression, to place a newline carriage-return where I would expect it to appear.

    1. I guess something like this should work:

      | sharedPackageCacheDirectory |
      sharedPackageCacheDirectory := ‘/Users/mariano/whatever/’ asFileReference ensureDirectory; yourself.
      MCCacheRepository default directory: sharedPackageCacheDirectory.

Leave a Reply