Real Project Management for Real Businesses

Browsing Posts published by Keith Casey (caseydk)

When we start projects, we often follow the naming conventions of our frameworks without even thinking about the “Why?” It almost seems silly to ask until you run into a – hopefully, legacy – codebase that has an incomplete or inconsistent scheme.

Unfortunately, web2project is one of those codebases.

For those just joining us, we forked web2project in late 2007 from dotproject which itself was started in mid 2000. Therefore some of the code goes back nearly 13 years into the dark days of PHP 3. Therefore, there’s a little.. cruft. And naming conventions are just one piece.

Regardless, there are some major benefits that come along with using proper (or at least consistent) naming conventions:

  • First, we’ve had a simple Object Relational Mapper (ORM) since the earliest days. It handles our object to database (and back) conversion with almost no configuration. While there are many arguments for and against ORMs, it works and makes things simple. In our case, we can add a field to the database, add it to the object, and finally the proper add/edit view and voila. It should just work. In fact, by using our configurable list views, you can add it to the proper lists entirely via the web interface.
  • Next, we surface those object properties to the form elements on the add/edit screens. It allows us to generate forms, validate the input, and move it along whatever the next step entails. There was nothing particularly unique here.

Where things got interesting was in the rendering (View) layer..

Previously we had a flock of little display inconsistencies. There were places where a date field was shown as a simple date on one screen, as a full am/pm datetime on another, and as a 24 hour datetime on yet another. Formatting for user’s name versus username was just as bad. While fundamentally, these issues don’t affect the core logic of the system, they demonstrate a lack of diligence and attention to detail. Besides, the number of bug reports we got on these were ridiculous.

So for the v3.0 release, we developed an HTMLHelper to standardize display throughout the system. It works quite simply by passing in the data we want to display along with the name of the field itself. For example, if we wanted to display a project’s end date, it would look something like this:

$htmlHelper->createCell('project_end_date', $project_end_date);

whereas if we displayed a task date time, it would look like this:

$htmlHelper->createCell('task_end_datetime', $task_end_datetime);

The method parses the field name to retrieve the datatype which is usually how the data is displayed. We end up with dates displayed as dates, budgets are displayed as currency, and urls are converted to clickable links. When you pass in a name – like project_name, task_name, etc – it will automatically link to a view of the object. This makes self-configuring templates start with reasonable defaults. Of course, you can still customize them but that’s your problem, not ours.

Unfortunately, there is one place the naming convention breaks down..

There are a total of total of 12 modules which have ‘name’ properties. Of those, four of them don’t follow the convention for module names, one doesn’t follow the convention for property name, and one has a completely different url pattern to view it. In short, this is a hairy mess. What should be three lines of code without any odd conditional processing turns into fourteen lines of code with twelve conditionals.

And this is one of the simplest places. The complex ones have dozens of lines of code with just as many conditionals.

Naming conventions are ridiculously powerful and useful.. and failing to follow them makes life difficult for everyone coming later.

You can read the entire Naming Convention specification on Github.

In the last few weeks, I’ve gotten a number of emails about our license change from Gnu Public License (GPL) to Clear BSD. While there have been a number of theories, I thought I’d share the actual answer.

Although I have talked and worked with a variety of lawyers on this situation, none of this is legal advice and should only be considered analysis by the leader of an open source project and not legal advice.

The license change primarily came about for a variety of reasons:

  • First, some people are forbidden to contribute to GPL projects. Their employers allow open source contributions via other licenses, but the GPL’s viral nature makes them nervous. Maybe inappropriate and not compelling by itself.
  • Next, the opportunity for others to build commercial successes on and with web2project ensures its longevity. If people make money with the project, it will continue to have supporters. I know of at least two companies doing this now. In both cases, they’ve passed back patches and made thoughtful (and likely helpful to them) architectural suggestions.
  • Next, the GPL would prevent us from interacting with proprietary systems or non-GPL compatible libraries[1]. Fundamentally, a project management system is about sharing information within and between groups. Quite often that information comes from other systems – CRMs, billing, time sheets – which may be proprietary or use non-GPL compatible libraries. If we were GPL, we would have to write/find our own libraries.
    • For example, I work for Twilio where we provide a REST API to send SMS (text messages) from applications. If I wanted to send text updates of tasks and web2project was GPL, I may be barred from using the MIT-licensed Twilio PHP library or have to distribute it separately making it more difficult for users.
    • Even more interesting, since the PEAR libraries within web2project core are under the PHP license, we are banned from including them without an explicit exception from the copyright owner[2]. Previously, Rasmus Ledorf (father of PHP) noted the Free Software Foundation (FSF, maintainer of the GPL) described “linking” in the sense of compiled software and literally said “Move along.” It was a dead issue but until the WordPress/Thesis GPL battle a few years ago. Things got interesting as one of the concepts put forward from many directions was nicely summarized by WordPress core developer Mark Jaquith[3]:

“It isn’t correct to think of WordPress and a theme as separate entities. As far as the code is concerned, they form one functional unit. The theme code doesn’t sit “on top of” WordPress. It is within it, in multiple different places, with multiple interdependencies. This forms a web of shared data structures and code all contained within a shared memory space. If you followed the code execution for Thesis as it jumped between WordPress core code and Thesis-specific code, you’d get a headache, because you’d be jumping back and forth literally hundreds of times. But that is an artificial distinction that you’d only be aware of based on which file contained a particular function. To the PHP parser, it is all one and the same. There isn’t WordPress core code and theme code. There is merely the resulting product, which parses as one code entity.”

Granted, PEAR libraries are not derivative works of web2project as themes are of WordPress, but this muddies the water.

  • Finally, the biggest reason was a potential risk to the data itself. I’m not saying that a tool would change the license of the content created or delivered through it. For example, if you write an original document in Microsoft Word, it is yours and not Microsoft’s. The FSF says that explicitly with:

“copyright law does not give you any say in the use of the output people make from their data using your program. If the user uses your program to enter or convert his own data, the copyright on the output belongs to him, not you.”[4]

Unfortunately, once again things were muddied in the WordPress/Thesis GPL battle. The concept is that if the application and a module/extension share in-memory data structures[5], they form a single program and if one is GPL, they both must be. But another portion of the FAQ adds an interesting spin:

“By contrast, pipes, sockets and command-line arguments are communication mechanisms normally used between two separate programs. So when they are used for communication, the modules normally are separate programs. But if the semantics of the communication are intimate enough, exchanging complex internal data structures, that too could be a basis to consider the two parts as combined into a larger program.”[6] (emphasis mine)

And that’s where things get interesting. In the case of WordPress, the data structure for a page or blog post is simple. There’s an object with fields like title, body, author, and a few other fields. The code to replicate that data structure would take most developers minutes to create. Even calling it a data structure is generous.

On the other hand, think about web2project. A project has tasks. Those tasks can be dynamic or milestones and have parent/child relationships and  dependencies. Then tasks have assignees who do work and log their time against each task and update its status which rolls up to the project status. And so far we haven’t considered contacts, files or other things associated with the tasks.

Using – let alone creating – these data structures is difficult with our existing code but – if that code was GPL –  any code exchanging those data structures may have to be GPL too. And every step closer to having the “right” data structure is another step closer to having the communications too “intimate.”

..but what *is* project management but the representation of complex data structures!?

Therefore to ensure the longevity of the project, respect the licenses of current and potential supporting libraries, and the integrity of our users’ data, we had to move away from the GPL.

  1. Drupal.org – Licensing FAQ
  2. Ben Ramsey – “What the GPL?!
  3. Mark Jaquith – “Why WordPress Themes are Derivative of WordPress
  4. GPL FAQ – “Is there some way that I can GPL the output people get from use of my program?
  5. GPL FAQ – “If a program released under the GPL uses plug-ins, what are the requirements for the licenses of a plug-in?
  6. GPL FAQ – “What is the difference between “mere aggregation” and “combining two modules into one program”?

For the record almost all of the GPL code is out of web2project as of quite a while ago. The only place is one single class where we limit our usage to public interfaces which are all being reimplemented. Our supporting libraries include those licensed under the BSD (adodb, Xajax), Lesser GPL (adodb, jscalendar, phpgacl, PHPMailer), MIT (jQuery),  PHP license (PEAR), QPL (jpgraph), or the public domain (ezpdf).

One of the most common configurations out there is related to allowing web2project users to have access to only specific companies. While it’s not as simple as saying “users should only see things from their own company,” it’s not as complicated as you might think. Here’s how I’ve done it for various groups.

If you start with the basic roles, here are the step by step directions:

Role: Project Worker

Non-Admin Modules – Allow – Access, Add, Delete, Edit, View
Companies – Deny – Access, Add, Delete, Edit, View
Reports – Allow – Access, Add, Delete, Edit, View

Explanation: This gives access for a User to do anything they want on any of the non-admin modules *except* for Company. But since all of my Projects are assigned to a company, they can’t actually see anything other than the navigation menu and empty screens.

Results: I just created a new User with *only* this Role. The only Nav options visible are Projects, Tasks, Calendar, Files, Contacts, SmartSearch, Links, Reports. Under each, there is no data visible other than information not associated with any Company… for example, some of the Contacts.

Now, I got back and add permissions to individual users:

Companies – CaseySoftware, LLC – Allow – Access, View

Results: The User can now view all the information associated with my Company. This includes all of its Projects, Files, Contacts, etc. This user could even create new projects if they wanted, but only for this Company.

Now, since this is a ficticious contractor user, I add the following permissions:
Companies – Acme Anvil Corporation – Allow – Access, View

Results: The User can now view all the information associated with this additional Company. Everything they could do/see for CaseySoftware, LLC now applies here too. Now, if they were working on this company’s projects, they could log time against tasks, whatever.

Now let’s say I have a single Project within CaseySoftware, LLC that the person shouldn’t see, so I add these permissions:

Projects – Secret Anvil Development – Deny – Access, View, Add, Edit, Delete

Results: This prevents the User from seeing *anything* involved with this project. No Tasks, no Files, no Calendar Events.

A few weeks ago, I spent a week at Microsoft Headquarters in Redmond, Washington representing web2project and working on SQL Server support. During the week, many people asked me variations of:

Why? What are you thinking? Are you dropping MySQL support? What in the world are you doing?

In some cases, their questions seemed more panicked that anything. To clarify what is going here, let me explain:

First of all, no, we are not dropping MySQL support. To be blunt, that would be dumb of us. Our community knows and loves MySQL. It’s installed on something like 103% of the web servers out there. For years, it has served as the foundation of web2project and we don’t plan to drop it.

Next, with respect to Microsoft.. their relationship with the Open Source community has ranged somewhere between global thermonuclear war and that awkward guy on the wall at prom. In some places, they’re doing good work while in other places, people are still aiming missiles. Regardless, some groups within Microsoft have worked hard to build positive, productive relationships with the PHP community.

Therefore, our goal is obvious. The goal was SQL Server Compatibility.

Our Vision for web2project is that we take over the world it can be installed into any company’s infrastructure and *poof* it works. Our users shouldn’t worry that their IT staff only supports SQL Server or prefers Apache over IIS or runs Ubuntu instead of Redhat. They just want their tools to work and we want web2project to be one of those tools, so the need was clear.

With that, I’m proud to announce that as a result of this week’s efforts, we believe we have full SQL Server support in the core system. I don’t (and won’t) know the compatibility of the Add On Modules, but if they’ve followed our suggestions in the Module Building Guide, they should be pretty close already.

My personal goal is to have SQL Server support ready for production use in the web2project v3.0 release this winter with at least one beta and one release candidate before then. If you know how to run SQL Server and would be willing to test, please contact me at caseydk [at] web2project.net and let me know. Any and all feedback is appreciated.

Disclosure: I have worked for Microsoft numerous times in the last few years and I continue to work with them in both paid and unpaid roles. Regardless, when they do something right, I applaud them. And when they do something dumb, I challenge them.

At php|tek 2011 last month, we had three of the five core web2project members in attendance. Despite my best efforts to protect the project by making sure we were never standing as a group (vulnerable to a meteor), eating together (vulnerable to food poisoning), or flying together (vulnerable to the Swan Station), cooler heads prevailed and we had a group picture.

Some of the web2project Team, May 2011

Some of the web2project Team, May 2011

From left to right are me (Keith Casey), our Testing King Trevor Morse, and Master of RESTfulness Benjamin Young.

And yes, there are now web2project shirts out in the wild. The first batch went to team members, any user I’ve met recently, friends of the project, and people who have helped us along. If you are interested in getting your own shirt, drop me a note:  caseydk [at] web2project.net  Once I have enough for an order, I will get pricing and notify everyone of the cost.

Or.. if someone wants to contribute $500, I can get a bunch printed and start sending them out immediately..