Tuesday, March 17, 2009

Misc IntelliJ tips

Here are miscellaneous IntelliJ tips. Some of them are very simple and yet took me a long time to discover. I hope you’ll find something new and useful among them. But please be aware that while using cool IDE features can make your work easier and more fun there is a limit to which they can help. After all, software development is not about using IDEs. “Use a Single Editor Well” is only one tip out of 70 in pragmatic programmer tips. Be aware also of baby duck syndrome and try another editor or IDE. Emacs, for example :)


DEBUG


When debugging you can see variable value under mouse cursor with alt + < left button click >

“Alt + click” can be more convenient compared to alternatives like pointing mouse on a variable, waiting for popup and then clicking on ”+”. Not to mention selecting text and using “Evaluate expression” action. “Alt + click” fits well with “browsing mode” (left hand on keyboard, right with mouse).


You can disable breakpoint with alt + < right button click on the gutter >

There isn’t much to say about it, just a fast way to disable one or several breakpoints. To disable all breakpoints it’s still easier to use “Mute breakpoints” in debug window.


You can create “tracing breakpoint” with shift + < left button click on the gutter >

This is just a shortcut for adding a breakpoint and then configuring it. By default “tracing breakpoint” will have configuration like in the picture below.


It’s easier to browse external stacktrace with stacktrace analyzer, rather than navigate to lines manually

While writing I found that stacktrace analyzer has already been mentioned in several posts. See JetBrains posts or post on java lobby. There is also a nice feature in stacktrace analyzer that it takes content from system clipboard, so that you don’t have to paste stacktrace in it manually. You select stacktrace in email (or where it is), copy it into clipboard, go to IntelliJ and press Alt+Z, S, Enter (I use menu :)).


If you want to find exceptions of which you are not aware, consider adding exception breakpoint

How well it will work depends very much on how exception are handled in your project. I found exception breakpoints useful while working on a project where the main pattern for handling exceptions is catching java.lang.Exception and writing stacktrace to log. You may silently get NPE and the only place to see it is the log file which has tons of other stuff. Moreover, you have to search log for exceptions manually. With breakpoint exceptions there is no way you wouldn’t notice the problem.

More generally it may be a good idea to have NPE breakpoint and breakpoint for uncaught exceptions to spot problems right away. (IIRC this is what VisualStudio does.)


If you debug objects which form a tree, consider using custom data type renderers

Basically, “data type renderer” is just a way to tell debugger what it should show and what should not. Here is post about type renderers in IntelliJ blog with more details. You can use type renderers for any type. I only found it useful to explore tree-like object structures. In particular to observe UI components hierarchy, antlr AST and IntelliJ PSI trees.


If you debug program with recursive (or complicated) call stack, consider marking instances to better understand it

Put simply, you can mark class instances so that to distinct them from other instances.

I had a hard time coming up with realistic example so here is not elaborated one. There is a Dog class with methods eat(Dog) and barkAt(Dog). Suppose that dog instances are dynamically created in some complicated way. You run the program and see the following call stack (in real world it will be diluted with calls on instances of other classes):

From the picture we see that the Dog#eat() method is being called recursively. It doesn’t necessarily mean that there is a bug in code. It may be that function is called recursively unless some condition is met. Conditions are usually based on object state so the above picture is not very helpful since it doesn’t show instance on which method is called. This is where marking instances can help. You go through call stack marking “this” objects:

And now, when stack shows instances of Dog, you can reason about what is going on.


If you have external logs files which you want to watch, consider watching them in IntelliJ

While there’s nothing wrong with using external editor to watch logs (for example, less waiting for new input) it can be easier to watch logs in IntelliJ. IntelliJ can filter out standard and error output and do usual text-file stuff like highlighted searching (with regexps).

There is “Logs” tab in the “Run/Debug Configuration” window where you can setup which log files to show (for example, latest of rolling log files). The downside is that with big logs and lots of input console window in IntelliJ doesn’t work very fast :(


BOOKMARKS


If there are several points in code to which you frequently navigate, consider using numbered bookmarks

There isn’t much to say about it. If you navigate to some class or method often enough, try numbered bookmark to see if it helps you to navigate faster. ctrl+shift+number to add numbered bookmark and ctrl+number to go to numbered bookmark.

Alternatively you can add classes and methods to “Favorites” lists (“Add to favourites” in context menu). See also bookmarks post in IntelliJ blog.


You can add bookmark with ctrl + < left button click on gutter >

Does the same thing as pressing F11. Can be better than F11 when you are in “browsing mode”.


TABS


You can close tabs and windows by clicking with middle button or shift + < left button click >

This feature was especially useful before IntelliJ 8, because there were no crosses on tabs with code. But it still works very well for closing windows. See also recent post in IntelliJ blog. This feature is not IntelliJ-specific. There are many other programs (it might be better to say “user interfaces”) which allow user to close tabs with middle button click (eclipse, firefox, opera for example).


You can see full path to file with ctrl + < left button click > on its tab

I don’t actually use it. I imagine it could be useful if clicking on folder in the popup would open this folder in external file manager. May be you have ideas why is it there and how to use it :)


TEXT


If you want to copy several text chunks from one file to another, it may be easier to copy them using clipboard stack

Suppose you want to copy three keys from property file and insert them into java code. Doing it “normal way” you would go to property file, copy one value, go to java file and paste it, then go back to property file, copy next value, go to java file and so on. There is another way to do it. You can go to property file copy all values you want (ctrl + c), then go to java file and paste them using clipboard stack (ctrl + shift + v). It’s simple and can save you from switching between contexts (which you do going back and forth between files).

You can also use numbers to paste text from keyboard. For example, if you want to copy three values, you can copy them into clipboard, go to the target file and press “ctrl + shift + v, 3, enter” three times.

To configure clipboard stack size see “Settings - Editor - Limits - Maximum number of content to keep in buffer”.


If you want to compare file with another one from outside of the project, you can use “Compare with clipboard”

Every now and there is a need to compare two files. It’s straightforward to do if both files are within project. You select these two files and choose “Compare two files” in the context menu. However, it’s not going to work if one of the files is not within project folder, because there is no way to select it. In this case you can copy content of external file to clipboard and use “Compare with clipboard” context action.

Sure, external diff programs can compare anything.


If you want to copy part of log without several left (or right) columns, you can use “column mode”

“Column mode” can be turned on it “Edit - Column mode” or with alt + shift + insert.

Alternatively you can delete text you don’t need with “Replace text” action using regexp mode.


You can copy opened file’s path to clipboard with ctrl + shift + c

You can also do it with folders in the project view. Useful to paste path into external file manager or console. See also IntelliJ features page.


If you want to use some constant or static method from another class, consider copying its reference

This is just a way to avoid typing class name and then constant/method name. Note that you can also use it to paste {@link ..} value into javadocs. See also IntelliJ features page.


Other


You can go to class or method by clicking middle button on it

Does the same thing as ctrl + < click > or pressing F4. Useful in “browsing mode”.


You can go to method or class implementation(s) with ctrl + alt + < left button click >

Useful in “browsing mode”. Alternatively you can open class or method hierarchy (it involves more fiddling, though).


It’s easy to see where checked exceptions are thrown by pressing ctrl + shift + F7 on catch/try keywords

It can also be handy if try-catch block catches java.lang.Exception. In this case it shows all checked exception the block catches. By the way, I still like alt + a much more than the default shortcut.


It’s easier to remove anonymous classes (try/catch blocks and etc.) surrounding some code with ctrl+shift+del, rather than do it manually

In case you haven’t seen it, take a look at IntelliJ features (unwrap). This works in IntelliJ 8 only.


Try “Appearance - Automatically position mouse cursor on default button”

If you’ve never used it, give it a try and may be you’ll like it. Positioning mouse on default button is not specific to IntelliJ, you can as well turn on similar option in your OS.


Finally, try using the latest version of IntelliJ by participating in Early Access Program

Most developers don’t like using “nightly builds” for real-world programming and this is very reasonable. We want to get our work done, not to struggle with buggy software. But there are also reasons to use development builds. The most compelling one is that you can use latest features (it assumes that they help you with what your work on). Another reason is that not all development builds are buggy. Sure, they have more problems than a release which has been out for a year (at least it’s supposed to be so), but not all problems might affect your work. It’s likely that you use only a subset of functionality and there may be problems in the parts which you don’t use or use rarely.

Regarding IntelliJ, I used EAP builds of 7 and 8 versions and from what I’ve seen EAP builds are good enough to be used for day-to-day work. So wait until April or so for IntelliJ 9 and give it a try ;)

Friday, February 27, 2009

Yak scratching

Recently when reading Thoughtworks blogs I coined the “yak-shaving” term. It means “any seemingly pointless activity which is actually necessary to solve a problem which solves a problem which, several levels of recursion later, solves the real problem you’re working on”. There is also an interpretation such as “doing it well now is much better than doing it perfectly later”, but I like the first one better.

As one can expect from working in a big company on “legacy system” it allows you to experience a lot of yak-shaving activities. For example, you want to catch breakpoint to understand a piece of code or make sure you change actually works (ask me why you cannot.. don’t write unit test). To catch breakpoint you would need database server on other continent, several feeds and services to be up (they can occasionally be down) and probably a remote desktop connection to market emulator which is shared by a whole bunch of people.

yak

After reading about yak-shaving I retold the story to several co-workers. Some of them didn’t get it, some (those who know the pain of yak-shaving) enjoyed it, but best of all I liked one response. I told a guy the yak-story, he spent about half-an-hour trying to get a breakpoint according to the above “methodology” and then exclaimed ”I’m scratching the yak”. This, I believe, is more precise description of what we sometimes do. You’re not just shaving it, but scratching. You may know with some degree of certainty how to get to the actual problem, but obstacles you face are so uncertain, unrepeatable and numerous, that despite all efforts you get nowhere and the only thing you left with is misery and despair. Indeed “shaving” sounds to optimistic in this case. “Shaving” assumes you’re making progress. But when you stuck with some totally unrelated problem for hours and then you get another one and then another, “scratching the yak” seems much more appropriate term.

Does it have to be this way? Why do we do yak-scratching? (I won’t go into five why’s.) What can we do about it? May be it’s our incompetence and lack of knowledge? May be it’s the way big systems are developed? Or may be it’s yaks’ conspiracy? From technical point of view we could separate system into modules with clear contracts. Develop modules separately. Create fakes for external systems and write automated tests. Sounds good but it requires political will. You have to convince management it will pay off for business. You have to convince people who work on project it won’t change one yak to another. Not to mention you have to be sure you’re right. (I realize it can be self-deception and blaming others is not a solution anyway.)

Not all technical problems are really technical. Beware of yaks.

Thursday, February 19, 2009

Debugging managers

The other day I was debugging the application I work on. At some point looking at the debug window in a “context free” way I realized that there is a whole lot managers in it and what I’m doing is basically debugging managers of managers.

It’s no that I think it’s a bad design or these classes are badly named (they could’ve been better, though). And it’s not that I think this structure is too complicated, after all there are only three levels of managers in the picture (actually more).

What drew my attention was the idea that choice of class names is influenced by organization, its structure and its language. The place I work at use model like: coding monkey –> manager –> superhero manager. Where the last two stages are obviously bound to be attractive. Now imagine how many times you can read the word “manager” in code (fields, parameter, local variables) given the huge number of manager classes. Admittedly it’s not very useful idea, since I can hardly imagine how one could benefit from it.

As the Conway’s Law (which sound like “any piece of software reflects the organizational structure that produced it”) the idea of code being influenced by corporate language boils down to the fact that it’s people who produce software and they inevitably leave traces.