Web development, consulting and project management | Programmation web, consultation et gestion de projets.

We use and favour open-source technology and philosophy. Our tool of choice is Drupal. Timely delivery, clear processes, healthy code wrapped up in a courteous and friendly approach.

Nous offrons également nos services en français!

Feel free to contact us and thanks for visiting! - N'hésitez pas à nous contacter et merci de votre visite!

Drupal Association Member

Civic Actions recently posted their Estimating Worksheet, a tool to help generate project proposals from Request For Proposal documents (RFPs). It's awesome that they are sharing this tool with the community (under CC Attribution Share Alike 3.0 license) and I would like to thank them for doing so.

The tool is a fairly complex spreadsheet which is quite well done. The worksheet approaches proposal generation in a similar fashion to the process we follow at Raincity Studios (my day job). It's not hard to imagine that a similar method would be used at other Drupal and non-Drupal software development shops.

The worksheet provides a structure for the breakdown of the information contained in an RFP into digestible tasks. Consequently, it becomes easier to attribute values to each of the site components such as work areas (like theming or engineering) and to estimate the time required to complete the tasks. The end goal is to generate an information set that helps define the scope of the project, attribute a monetary value to it, and generate documentation to be submitted to your potential client.

The rest of this article assumes that you have a basic familiarity with proposal generation, project scoping, and production management. Furthermore, some of the terms used may sound cryptic if you haven't yet had a peek at Civic Actions' Estimating Worksheet.

Make it Two

Two aspects of this worksheet that I feel are refreshing and that have the potential to bring a clearer perspective to the process are:

  1. building two concurrent proposals - one based solely on the RFP and the other that accounts for your recommendations; and,
  2. the Certainty Factor.

Let's look at each of these in a bit more detail...

The Recommendation Estimate sheet allows for the generation of a totally separate proposal based on the RFP requirements and what you, as a Drupal expert, estimate would be an appropriate solution to meet the client's requirements. This contrasts from traditional RFP-bound proposal generation, as it allows for matching features with out-of-the-box Drupal functionality in order to simplify development/maintenance and potentially lower project costs.

For example: The project requires feature X that, if implemented as expressed in the RFP, would take Y hours to complete. However, you may suggest an existing contributed module which can meet most of the requirements, in a slightly different fashion, for a fraction of Y.

In RCS proposals, there is often a set of requirements that contain more than one associated cost estimate. As a result, it is difficult to come up with a “final number” that takes into consideration the potential variations in how features might be implemented.

Civic Actions' tool provides a very interesting way of viewing different sets of information (i.e. two separate proposals). This can facilitate discussion with clients about the different ways a project could be built. (Check out how the “RPB” column makes this process painless!)

Now let's have a look at the Certainty Factor...

It's always a challenge to assign a satisfying completion time estimate to a feature with a lot of unknowns (e.g. one that is poorly-defined or requires the use of cutting-edge technology). This is especially true in the context of projects with a tight budget or timeline. The spreadsheet includes the concept of Certainty Factor, which rates the level of uncertainty you might have for any given feature. A Certainty Factor for the entire project is also generated.

Having high/low estimates can provide a useful launching point for discussing with your client the features that are to be kept or dropped from the project; those that can be simplified or enhanced; and those which can be moved to subsequent phases of the project.

I can think of another potentially interesting use of the Certainty Factor. It could also be used as a good indicator of the types of projects your company wants to take on. Depending on your team's resources (availability, skills, experience, etc.) and the type of clients and constraints you would be working with (budget, timeline, client attitude, etc.), you may conclude that a project with a Certainty Factor greater than value X presents a risk factor too high for your organization. You can then pass the lead on to other Drupal agencies who would be better suited for this type of project.

Similarly, if you're interested in being on the bleeding edge and like to take risks, or if your developers need something new and exciting to work on, you may want to look at projects with a greater uncertainty factor.

Give it Some Time

One of the weaker aspects of this tool relates to project duration. Unless I missed something, the project duration is not a calculated value. I am sure it's possible to guess a time span based on the size of the project, available resources, and experience. However, I think that if intuition is combined with a more rational approach, a more precise estimation is to be expected.

In the spirit of releasing early and often, I am pleased to contribute to this tool by adding a system that can help you determine the project duration with better accuracy. Three sheets have been added to the Estimating Worksheet to create version 1.2 (?) of the document .

Here is an overview of the added functionality:

  • The Resources sheet is where you enter the name of your team members. You will also be able to associate each of your resources with a weekly “production time”.
  • The Assignments sheet is where you couple a Resource with an Area of Work.
  • Areas are high level task groupings. Areas were available in the 1.1 version of the document. However this new Areas sheet abstracts them a step further. Areas can be defined on a project basis but they will most likely always be the same across projects. This sheet also gives you an overview of how much time each Area will take to be completed, based on available resources.

Other features are:

  • Ability to determine the level of “involvement” a resource would have in a project.
  • Ability to assign a resource to multiple Areas.
  • Areas dependencies (single) (i.e. Area C can depend on Area B, but not on Areas A & B ).
  • Areas durations inheritance (i.e. Area C start date depends on Area B , which depends on Area C).
  • Generation of low, high and average project duration.
  • Anticipated start date and Estimated end date.

Of course, there are shortcomings - this is, after all, a spreadsheet... Here are a few I can think of: multiple dependencies, exceptions to schedules (e.g. for vacations, sick days, etc.) and ability to view resource allocation across multiple projects. Regardless, I feel this constitutes an overall improvement on the 1.1 version. I would be happy to continue to collaborate in making this tool better.

Please read the notes embedded in the document. Thanks for reading!

I have been meaning to write about this topic for a while now. All the bits have been waiting for the right moment to be assembled. For several years, have been working with the Conseil scolaire francophone de la Colombie-Britanique (BC Francophone School Board) in developing and maintaining their job board application (https://emploi.csf.bc.ca/). I know, I know, it doesn't look very innovative from the outside, but there are some very useful admin tools in the back end. It's true, I swear.

As the site is built for francophones, all the content needs to be available in French. I have put together a simple step-by-step recipe for module creators and translators who need to have their site in a language other than English. Even if you have no immediate need for a translation of your module, providing a translation template will allow other contributors to create their own translations. Note that this recipe is Drupal 5-specific but doing this for Drupal 6 would be very similar.

Getting going and generating the PO Template

Generating the POT file is the minimum you can do - beyond not doing anything at all. This is the template from which all of your module translations will stem.

  1. First off, you will need to get the the potx module (http://drupal.org/project/potx) and the gettext package (http://www.gnu.org/software/gettext/#TOCdownloading).
  2. From the potx module folder, copy potx-cli.php and potx.inc to your module directory.
  3. Navigate to your module directory and create a folder named po.
  4. Make sure that potx-cli.php is executable [ $ chmod +x potx-cli.php ] and execute it [ $ ./potx-cli.php ].
  5. This will generate a template file named general.pot - a PO Template file.
  6. Move the newly created .pot file to your po directory and rename it with your module name while keeping the .pot extension.

Creating a PO file

If you need or want to translate a module (your own or someone else's) you will need to generate a PO file out of a PO Template. The PO file is the file that will actually hold your translated strings. This is how you can do it:

  1. Navigate to the po subfolder of the module folder. There you should see the .pot file and maybe some .po files, if translations already exist. If your language PO file is there, well, you're in for the easy ride. You may pass go and collect your dough. If not, it's gonna take another turn...
  2. Generate an empty PO file using the msginit utility [ $ msginit --locale=ll_CC ] where ll_CC is the locale (ll the language code like “fr” and CC the country code, like “CA”). From what I gather, you may simply use the the language code. For example [ $ msginit --locale=fr ].
  3. If all goes well, you should now have a PO file (per the above example we would have fr.po). Now is the time to put your translator skills to work.

Keeping your POT in the game

As your module evolves, translatable strings may be added, removed or simply moved. In order to keep your translations up-to-date, you will need to keep your POT up-to-date.

  1. Go to your module directory and generate a new POT file per the steps described above.
  2. Copy the new POT file over the one in the po folder.
  3. Use the msgmerge utility to generate a new PO file that merges the “structure” of the template and the existing translations [ $ msgmerge -U def.po ref.pot ]. The -U flag is for update; the def.po is your existing PO file and ref.pot is the new POT file. Msgmerge should create a backup of your PO file (look for a PO file followed by a tilde ~). But, until you can confirm that your version of msgmerge does it for you, I'd recommend making a backup copy yourself.

There you are! Translating Drupal modules is no longer a secret for you. Now getting the translation right can be another challenge!

Oh. last words of advice: use English in your module and wrap your strings with the t() function, otherwise gettext/potx-cli.php will not pick up your strings.

If you are like me and spend many hours per day interacting with the world-out-there-via-the-web, you surely have developed preferences in the way you like and expect these interactions to take place. One simple example of this is returned search results and more specifically domains that have high ranking and yet little use for one's circumstances.

Here is a simple way to remove these undesired domains from your search using Firefox and the Linux Mint Google search plugin which I have mentioned here before. Although this is quite specific, I know this can be easily adapted to various OS and search plugins.

  • First, locate the Firefox directory "searchplugins". In our case, it could be found at /usr/share/firefox/searchplugins
  • Edit the appropriate xml - google.xml, in this specific case - file with your favourite editor. Add the following line as a search parameter: <Param name="as_eq" value="site%3Aexample.com"/>.
  • Save and enjoy!

Here's what my google.xml file looks like:

<SearchPlugin xmlns="http://www.mozilla.org/2006/browser/search/">
<ShortName>Google</ShortName>
<Description>Google Search</Description>
<InputEncoding>UTF-8</InputEncoding>
<Image width="16" height="16">[--- snip ---]</Image>
<Url type="application/x-suggestions+json" method="GET" template="http://suggestqueries.google.com/complete/search?output=firefox&client=firefox&qu={searchTerms}"/>
<Url type="text/html" method="GET" template="http://www.google.com/cse">
  <Param name="cx" value="002683415331144861350%3Atsq8didf9x0"/>
  <Param name="q" value="{searchTerms}"/>
  <Param name="ie" value="utf-8"/>
  <Param name="oe" value="utf-8"/>
  <Param name="cof" value="FORID%3A1"/>
  <Param name="sa" value="Search"/>
  <Param name="as_eq" value="site%3Aexperts-exchange.com"/>
</Url>
<SearchForm>http://www.linuxmint.com/start</SearchForm>
</SearchPlugin>

The first link that shows up in my autocomplete browser history when I type “dr” is http://drupal.org/node/321. There is a very simple explanation for this. This is the node I refer to when I need the CVS checkout command (the “download” command in CVS speak), that allows me to obtain a particular version of a Drupal contributed project (i.e. a theme or module). This is the line that I look for on that page:

cvs -z6 -d:pserver:anonymous:anonymous@cvs.drupal.org:/cvs/drupal-contrib checkout -r DRUPAL-5--1-0 -d moduleName contributions/modules/moduleName

Why use CVS instead of getting the tar ball directly from the project page? Two words: easy maintenance. Here's a little recipe that will make your life easier...

Footwork

First off, identify which release of the module you want/need to get and figure out the corresponding tag (the “release” or “version” in CVS speak) syntax. Identifying which release to use may require a bit of reading but generally you will want to go for the latest.

As for determining what tag the chosen release has, there are at least two avenues:

You may go to the module page and figure out the corresponding revision tag based on the particular release. Let's use the "views" module as an example. If I want to checkout the 5.x-1.6 release, I may be able to figure out that the CVS tag is DRUPAL-5--1-0. But what about, say, release 6.x-2.0-rc3?

This is where the second avenue may come in handy: Drupal's browsable CVS repository (http://cvs.drupal.org/). If I navigate to http://cvs.drupal.org/viewvc.py/drupal/contributions/modules/views/, I will be able to see the different releases available for this module by looking under the “Sticky Tag” drop down menu (see below). It now becomes much easier now to find out that the tag name for release 6.x-2.0-rc3 is DRUPAL-6--2-0-RC3.

Views module releases as seen on cvs.drupal.org

Now that I have this basic information, I can checkout the the module to my development machine.

$ cd /var/www/mysite/sites/all/modules
$ cvs -z6 -d:pserver:anonymous:anonymous@cvs.drupal.org:/cvs/drupal-contrib checkout -r DRUPAL-6--2-0-RC3 -d views contributions/modules/views

Fancy Pants

Now, if you want to work in a smart way, versioning your own code is a good place to start. I personally use subversion (svn), but there are several other options out there (http://en.wikipedia.org/wiki/Revision_control). The question here is: how do you combine and take advantage of CVS (Drupal's code) and svn (your code)?

Once you have checked out the module using CVS as we did above, simply add and commit (the “upload” in svn speak) the new code to your svn repository:

$ cd /var/www/mysite/sites/all/modules
$ svn add views
$ svn commit views -m”initial commit of views release 6.x-2.0-rc3”

The new module is now part of your repository and may be checkedout onto your server!

Hat Trick

So what's really cool about this process from a maintenance perspective is that next time a new release of a module comes out, you can simply update the module code rather than having to download/un-tar/overwrite. And if you use svn, your benefits will be even greater.

Let's look at what would need to be done if a rc4 release of "views" became available and I wanted to deploy the code both locally and to a remote sever:

On my development machine (local)
$ cd /var/www/mysite/sites/all/modules/views
$ cvs update -dP -r DRUPAL-6--2-0-RC4
$ svn ci -m”update views to release 6.x-2.0-rc3” 

And on the remote machine:

$ cd /var/www/mysite/sites/all/modules/views
$ svn up

You'll be done before the coffee is even ready! Bookmark node 321 and this page!