Archive for September, 2006

PollPress WordPress Plugin

Andy on Sep 11th 2006

Download: PollPress 1.0
Subversion: PollPress 1.0

Regretfully, PollPress is no longer a supported plugin.

Purpose

PollPress is a plugin that allows you to add polls, similar to sites like slashdot, to your blog. Poll creation and management is very similar to creating and managing normal posts. The plugin allows users to vote on the most recent poll from the sidebar, and the poll results are displayed in a post, where users can comment. The plugin also adds an archive page for the polls, where users can browse and vote on older polls.

Requirements

PollPress 1.0 requires WordPress 2.0.4 or higher, and MySQL 4.1 or higher.

Installation

  1. Download the PollPress plugin.
  2. Extract the plugin from the zip file. You should get a folder named PollPress. In it you will find a file called readme.txt and the actual plugin folder called pollpress.
  3. Upload the inner pollpress folder to your plugins folder, which is usually called ‘wp-content/plugins/’.
  4. From the Plugins administration panel, activate the PollPress plugin.
  5. To install the voting booth on the sidebar, you need to add some code, <?php pollpress_voting_booth(); ?>, as described next.
  6. In the administration panel, click the ‘Presentation’ tab, then the ‘Theme Editor’ tab.
  7. In the theme files list on the right, click on ‘Sidebar’.
  8. In the code, find the desired location in the sidebar to add the voting booth. At this location, insert the code <?php pollpress_voting_booth(); ?>. If the sidebar is like most, you will need to put it inside list item tags, like this: <li><?php pollpress_voting_booth(); ?></li>
  9. Press the ‘Update File’ button.

Use

Writing and managing polls work almost identically to writing and managing posts. PollPress installs administration panels under Write > Write Poll, Manage > Polls, and Options > PollPress. The sidebar of the site will always show the voting booth for the most recently published poll. PollPress will also automatically install a static page called ‘Polls’ that lists all the polls that have ever been published. Users can use the Polls archive page to find old polls and vote on them or view their results.

Writing a poll is simple. Navigate to the Write > Write Poll panel. Enter a title and, optionally, your first poll option. Press ‘Save and Continue Editing’ or ‘Add’ to save the title and option and continue editing. All the extra settings such as Author, Timestamp, Category, etc work identically to a post. When you are ready to publish your poll, press ‘Publish.’

Managing your polls is the same as managing your posts. The only difference is that instead of going to Manage > Posts, you go to Manage > Polls. You can view, edit, and delete polls from this panel, in addition to managing comments posted to the poll results.

The options for PollPress are minimal, and are found in the Options > PollPress panel. The options allow you to change the color of the bar graph on the poll results page. The options page also provides a button to delete all the polls. Because PollPress uses a filter to generate the poll results, if you deactivate PollPress all your polls will begin appearing as regular posts, but with no content. So if you wish to uninstall PollPress, press the ‘Delete all polls’ button first, then deactivate the plugin.

Screenshots

Click on a thumbnail to see the screenshot at full size.

PollPress voting booth Voting booth Poll results Poll results
Polls archive pageArchives page Writing a pollWrite a poll

Support

PollPress is no longer supported. I will not be fixing bugs or adding any features. The code is open source and can be improved by others.

Filed in PollPress, WordPress | 148 responses so far

Help Elaine get her Masters in Education

Andy on Sep 9th 2006

Elaine is working hard on completing her master’s degree in Education. I know, I’ve seen her do it. In order to complete her quest, she not only needs to jump through hoops set ablaze, and stick her head in the mouths of large carnivorous animals, she also has to take a class in educational research.

Part of the class requires her to do, ahem, research. Right now that means she needs you, the person reading this, to take a survey on how you learned all your mad technology skillz.

In case you missed it the first time, here’s the link again:

http://www.surveymonkey.com/s.asp?u=165762519174

Please take the survey and send it to your family, friends, enemies, and those people who click on links in spam emails. They’re liable to click on just about anything, and it might as well be something useful.

The survey is only open for two weeks, so act quickly!

Filed in Personal | No responses yet

Respect for the testers

Andy on Sep 7th 2006

Sure it’s a lot fun to tease them and try to make their lives miserable, but really, if we didn’t have testers who would we, as engineers, have to torment? The marketing people? Please, they’re not even self aware enough to know that we’re doing it, and that’s no fun. Testers, on the other hand, are not only fun to use as scape goats, but they also provide an important service for the product.

Namely one I never want to do.

Despite that, I found myself doing exactly that recently. My WordPress plugin is now code complete, but is in need of testing. I looked around the apartment for suitable candidates, but the lizards around here are so small they cannot even depress the keys on the keyboard despite jumping on them. That’s how this unmentionable task fell to me: I had to write and execute test plans.

GAAAHHHH!!!!

Now writing test plans and such is something that I learned about in college. At the time I thought “Bah! This is nice for reference and all, but I’m never going to use this. I’m an engineer! I create the bugs, not find them!” Oh, how wrong I was. While in college, I also worked as an intern. Although I was supposed to be working on developing internal tools, I often got pulled into doing QA work. (Note for the unexperienced: the QA department is always understaffed. Hide behind the nearest potted plant if the QA manager ever comes within ten feet of your cubicle.) It was a never ending battle: me trying to escape QA work, the QA manager pulling me back in, and the other engineers laughing at me the entire time.

Testing and quality assurance work is never fun. When writing a test plan, you have to think of all the possible ways that a feature can break, and make sure all the different angles are covered. But that’s balanced by the fact that you can’t test everything so you have to be smart about what you test. That way you get the maximum possible coverage for the least amount of work. After you write the mind-numbingly boring test plan, some unlucky bloke has to run it. The experience is much like putting a portable drill to your temple and pressing really hard.

I’ve actually managed to get the test plans for my plugin written now. I found that writing them myself was a good exercise. I had to change my attitude from “how do I make this work?” to “how do I crush this pathetic excuse for software, and send the developer running home to his mommy?” I found several bugs just by thinking through how to test the different features. I also found that there were features that weren’t as usable as they should have been, since I hadn’t been looking at them from the point of the user, but that of an engineer. All of this, and I hadn’t even run the test plan. Good stuff.

I’m not looking forward to running my test plans. I have to run them at least three times: once on Safari, once on Firefox, and once on my arch-nemesis, Internet Explorer. May God have mercy on me.

I say all of this to show that I respect the testers and quality assurance people out there. Sure I go through this each time I have to do some sort of testing myself, or a tester finds a bug that I wouldn’t have caught myself, but it bears repeating. Testers are there to make to make the engineers look good. Unless the tester wants your parking spot. Then they’re probably trying to get you fired so they can have a shorter walk to the building.

Filed in Programming, Testing | No responses yet

It’s not about code reuse, it’s about maintenance

Andy on Sep 3rd 2006

Uli Kusterer has an article on his blog about what he calls “Cocoa ground rules.”

Since I’ve seen many people violate two ground rules of object-oriented programming (OOP), I thought I’d list them here, in the hopes it’ll help some beginners not fight the frameworks but rather go with the flow in Cocoa:

Uli then lists encapsulation and designing for code reuse as the ground rules. Now Uli is giving some good advice here, but I’d like to nit pick him here a bit for my own personal agenda… I mean, for the good of the people. Yeah, that’s it, the good of the people.

I propose that designing for code reuse, in most cases, is not the best thing to do. Allow me to explain.

Think about the times that you actually reuse code, in real, live applications. Its usually data structures, generic algorithms (like sorts and searches), and standard controls. Now think about where you find such code. That’s right, the basic data structures, algorithms, and UI widgets that you reuse in different applications are provided by the operating system or language for you. You don’t need to implement them, and, in general, shouldn’t try to. Apple is smart and realizes that applications get developed faster when developers don’t have implement basic data structures etc, that the operating system could provide for them.

Since the operating system and programming language provide most, if not all reusable classes, what’s left in your application is the application-specific classes. By definition application-specific code doesn’t typically have reuses in other applications, unless you’re writing competition for yourself. For example, if you have a class that reads in a SVG document, then you are probably drooling on yourself from having to read that insane specification. Plus, its unlikely you’ll need that SVG reader class in another application unless its also a SVG editor.

Now some of you think you have just spotted a hole in my logic. What if you have an application that is a lightweight SVG viewer and then a full-featured vector editing application? Both are plausible products that would need a class to read SVG documents. But they will have very different uses of the SVG reader class. The lightweight viewer will want to quickly build up the graphics state and draw, while the editor will want to keep the SVG DOM around so it can be edited later. Not a problem, you can abstract the SVG reader class to simply use callbacks on the delegate and let the delegate build up a DOM or whatever it needs to do to be efficient. That fixes the problem.

Right?

Except that the whole “abstracting” part is real hard. Very hard, especially if you haven’t implemented all the possible users of the class yet. As any API designer will tell you, it’s difficult to anticipate how a class is going to be used. That can lead to one of two situations: a class that isn’t abstracted enough to be used by multiple client classes, or a class that’s over engineered and very hard to use. Neither is ideal, but I will argue that being over engineered is worse.

Over engineered code is often bug riddled because of its complexity. It also runs the risk of having untested code in it, where the implementor said, “I don’t need this method now, but someone might need it later.” This introduces code that may or may not work, but creates the illusion, by being in the codebase, of being tested. That’s very bad. Over engineered code, as a result of being complex, also has a higher rate of being abandoned by potential users. If another programmer can’t figure out a class, they’re much more likely to create a new class to do what they want. On the other hand, if they see a simpler class that they understand, but doesn’t quite do what they need, they are more likely to enhance it to meet the original need and theirs as well.

I’m not saying code reuse is bad, I’m saying code reuse as a goal can be bad. In the stead of code reuse, I propose a new goal (or old, depending on how long you’ve been around).

As I so convincingly showed above, achieving code reuse is quite often not an attainable or realistic goal, because it so rarely happens. But what does happen a lot, and is in fact inevitable, is code maintenance. No matter what you write, you will have to maintain it at some point, unless you write really crappy code that no one in their right mind wants to use. There are several reasons why maintenance is more important than reuse:

  • Money. More money is generated from product upgrades (maintenance) than the initial release.
  • Time. Maintenance is where the product spends most of its life cycle.
  • Code reuse itself. As I said above, most code reuse is achieved by modifying simple classes to meet the needs of additional clients.

Now that everyone knows that code maintenance is where developers spend their time, and make their money, we should optimize for it. How do we do that? Well, we need some new ground rules for that.

The ground rules of any programming, whether object-oriented or otherwise, lies in two terms: cohesion and coupling. Hopefully you remember these terms from your computer science classes, but in case you were getting a bikini wax that day, I’ll define them.

Cohesion describes the internal relationship of a module, or in OOP terms, a class. High cohesion means that everything in the class is tightly related (e.g. the x and y member variables in a point class), where low cohesion means that everything inside is only loosely related, if at all (e.g. the Windows Registry).

Coupling describes the external relationships of a module or class. High coupling means that a class is very dependent on other classes, such as deriving from them or declaring them as friends. Coupling can also be the use of other classes or aggregating instances of other classes. Low coupling means that a class or module pretty much stands on its own. i.e. It doesn’t need other classes to compile or run.

Ideally, you want high cohesion and low coupling.

High cohesion and low coupling improve code maintenance in some simple ways. High cohesion means you don’t have to go searching everywhere in the codebase to find everything about, say, vectors. Its all in one place. Which means the code is easier to understand, and also modify. Low coupling also means that code is easier to understand, because you don’t have to understand how several classes work (such as a class and its parents and friends), but just a minimal set. More importantly, low coupling means the code is easier to modify. Since code isn’t tightly coupled, then you can modify code in one class and not have to worry about it effecting a class its not coupled to. This extremely important in large software systems, like when you’re trying to figure out why moving a button in a dialog changes how your preferences are written out.

“Fine”, you say, “I want high cohesion and low coupling, but it sounds like proper encapsulation will get me that, which in turn will lead to code reuse, easier maintenance, and incredible abs. How is that any different from what Uli said?”

The goal is different. You’re goal is not code reuse, although it might be a welcomed side effect. Your goal is easy code maintenance. Focusing on how to make things easier to maintain, as opposed to reusable, changes how you code your classes. Instead of spending time trying to guess all the possible uses of a class and making them generic as possible, you code it to satisfy the needs of its current clients efficiently. As different clients require its use, then you modify the class to accommodate them.

In all fairness, reusability for Uli is really important. But its not because of programming ground rules, its because of product requirements. Uli has lots of sample code, and the primary feature of sample code is reuse. That said, I would still argue that it is more important that the sample code be maintainable than outright reusable by everyone. Its impossible to guess all the possible ways a Cocoa view could be used, so its more pressing that it can be understood and modified by the user to do what’s needed.

In computer science you should always optimize for the common case. Which is code maintenance, not code reuse.

(P.S. My apologies to Uli if I have misrepresented anything you said. Your comment on code reuse got me thinking about the people who rant and rave about code reuse as if it were the Holy Grail.)

Filed in Programming | 2 responses so far

Joel’s Wasabi: not a bad idea

Andy on Sep 2nd 2006

Recently, Joel Spolsky wrote an article entitled “Language Wars.” In it he spoke about web frameworks and languages, and their appropriate uses. He basically said Java, .NET, PHP, and maybe Python were the only ones you should really bet your business on. He also snubbed Ruby on Rails as not being proven.

That didn’t sit well with some in the Rails community.

However, what really set them off was that at the end of the article, Joel mentioned that they use their own custom language, Wasabi, for their flagship product, FogBugz. How could Joel deride Rails as being unproven, which has been around for a few years, and then say he used his own custom language? Clearly this was an ironic contradiction.

Right?

No, not really. Joel’s point was, when picking a web language, it should be proven. More specifically, Joel mentioned that it should be known that it can scale, and have all the features your web application might need. PHP/.NET/Java have been around enough and used enough by large web applications that its well known that they have both of these qualities. Ruby on Rails, while very promising, doesn’t have the reputation of being proven yet. I suspect in a few years Rails will have this reputation, but right now its too young.

The reason using Wasabi isn’t a contradiction is because it isn’t what ships. Wasabi isn’t the language that runs on the server or what Joel’s customers get when they buy FogBugz. Wasabi is just the front end language that compiles down to PHP or VBScript, which is what the customers get. It doesn’t matter if Wasabi can scale or if it has all the features FogBugz needs. If Wasabi doesn’t have a feature FogBugz needs, they just add it to the front end. Since the backend only targets PHP or VBScript, the feature will already be there.

What’s more, is when Ruby on Rails becomes proven and surpasses PHP, Java, and .NET, then Joel can modify Wasabi to target Rails. He doesn’t even have to change the code to FogBugz to do that.

So when comparing Ruby on Rails to what Joel bet his business on, you can’t compare Rails to Wasabi, you have to compare it to PHP or VBScript. That’s what the customer sees, and that’s what the product is implemented in. My point is, Joel isn’t betting his business on Wasabi. He’s betting it on PHP and VBScript.

Filed in Programming | 3 responses so far

Bad Behavior has blocked 710 access attempts in the last 7 days.