From the beginning, Concrete has been designed as a system that makes the creation of pages easy, with a flexible "block" system available for placing items of content within these pages. As Concrete has matured, new data types have been created for different types of tasks. In Concrete5, for example, we have all sorts of these: single pages, page types, themes, blocks, elements, user attributes, page attributes, email templates, and more.

These items have to be stored somewhere, and that means breaking them up into the filesystem, into directories that make sense, which hopefully can be understood at a glance. However, care has to be taken with this, because another goal in Concrete5 has been the ability to easily centralize 99% of what Concrete5 provides, so that one server can run many Concrete5 installations with a shared code library. In Concrete5, all of the items listed above can exist in one central spot, but still be referred to (and overridden) on a site-by-site basis.

Furthermore, Concrete5 introduces the concept of packages to the Concrete universe: all of the items above can be "packaged up" into groups of functionality, and installed into a particular Concrete5 website. Packages can be as disparate as "Blogging System," "Software Support Forum Center," and "20 Killer Themes!" Once these items are unzipped and placed in the packages directory, they can easily be installed in the dashboard.

My point? Concrete5 is a complex beast, and whether a particular bit of functionality is available as a shared library on a web server, is part of a package, or is a unique item for just one website, the system still needs to be able to find it. As you might imagine, in a system this complex, it might be difficult to find what you're looking for.

Cut to last week, in the middle of a hectic workday. "Where'd the blocks directory go?" Tony asked, after a break from working on Concrete5 for a little while, during which much of the package functionality was updated. I was somewhat flustered, and didn't have time to give him more than a perfunctory: "It's in concrete/packages/core/blocks/"

He was silent for a second, then asked, "Don't you think it's going to be hard for people to find in there?"

I wanted to explain the reasons for this decision; that, it makes it easier when we know all blocks that are installed in the shared space are contained within some kind of package, and can use those functions to locate their files in the filesystem. So most of Concrete5's core functionality is actually contained within a "core" package, which lives in the packages/ directory, and is automatically installed along with Concrete5.

I didn't have time to make this response, though; instead, for the first time in a long time, knee-jerk developer mode kicked in. I'm not sure what I said, but it was probably something like "Once we have good documentation up on the filesystem, people will know where they have to look."

Later, while mulling over the exchange, I wanted to further rationalize this choice, but I couldn't: he was right. It was hard to find in there, and it was annoying to work on. Why should these core bits of content be inside a package that was always going to be there, when they themselves were always going to be there? Weren't packages by their nature optional extensions?

They were, and the fact that a "core," "required" package existed meant something was wrong. Corners were being cut in the name of the system. The end user – in this case, the developer looking through the filesystem, hoping that its structure is intuitive enough to understand without reading the documentation – is being sacrificed for the ease of the Concrete5 developer, who'd rather shoehorn everything into a "package" so that we don't have to tell the system to look in yet another place for some of its core files.

But this is wrong. So much work has gone into making Concrete5 a great system for users of the content management system, that it'd be a same if the same care weren't taken with developers and extenders of the content management system. The goal for Concrete5 has always been a content management system that humans could understand and love; we just need to remember that developers are human too.

That's why, if you check out the latest version of Concrete5 in subversion (this hasn't made it to SourceForge yet), you'll notice that directories like "blocks," "themes," "single_pages" and "elements" have moved into the concrete/ directory, where they can easily and intuitively be found. Additionally, these items can also be installed within a specific website as well. And to answer your question before you ask it: packages still work. Yes, it was a lot of work tweaking the system so that all the various places for these items are checked in a sensible order of precedence, but that's ok, because it's the system that should be doing the hard work, not the end user. And for now, the packages directory remains blissfully empty, which is as it should be.