Website Re-Development
Until very recently, this website was powered by Drupal. Now although Drupal's great in a whole raft of situations, there are times when either it's overkill for something small, or just doesn't fit into one's workflow. I came to realise that both of these applied to this site, so when it came to re-developing, I decided to abandon Drupal for the site altogether.
In the end, I decided to rebuild the site using Jekyll, along with a few other tools along the way.
This post explains the motivations behind the decision, what I did next and some of the challenges I faced along the way.
The Need for Re-development
There were several aspects that made re-developing my site something of a priority.
First, it wasn't mobile-friendly. I may have been able to get away with that some years ago when I first drafted the site, but now that's just not acceptable. After weighing the pros and cons of a responsive vs a separate mobile site, I decided on the former - and the only way to do that would be to start the front end build again from scratch.
Secondly, the site was running Drupal 6. When I first built the site, Seven was in the offing, but not yet secure or stable enough for production. Staying with Drupal would have meant an upgrade, and moving between versions 6 and 7 isn't trivial.
Lastly, the structure of the site was no longer ideal. My work of late has included open-source development and lots of writing, so a portfolio only told half the story.
Other Factors
Workflow
Though the entire site was content-managed, the vast majority of my time was spent on the blog - the rest rarely changed. Although I had a WYSIWYG editor installed I was far more likely to use raw HTML, and often use the tools I use every day - such as Sublime Text - and then copying between applications, rather than editing in the browser. As such, it made sense from a workflow point-of-view to switch to something that closer resembles my development process.
I've also become quite a fan of Markdown of late.
Bloat
For such a simple site, there sure was a lot of it.
Performance
There were time when the site ran pretty slow. Largely this was down to the fact that I have all sorts of projects running on the same box, and also because there have been times when the site has taken something of a hammering - particularly whe I release a new article. I wanted my site to perform the best it possibly could, without throwing server resources at the problem.
Curiosity
Then there was the final motivation - I wanted to try something a little different. There's no doubt that moving sites from a CMS to static is quite "cool" right now; maybe there was an element of that, but it's also true that the vast majority of the projects I'm involved in use frameworks or CMS's, and I wanted to try stripping back the complexity of those, and try something new. Enter Jekyll, which although I'd looked at I hadn't really used.
What had to Go
In moving from a fully-featured CMS to a static site, there were a number of things that would have to go - or, at least, be re-thought.
Comments
Most of my posts attracted some excellent comments. Clearly comments are something that aren't supported with a static site, at least without using something like Disqus.
However, with comments you always have to weigh up the pros of inviting discussion and gaining useful insight, with the effort involved in fighting spam. I used a number of the tools at my disposal to help the fight on my Drupal site - primarily, moderation and Mollom. I deliberately opted against CAPTCHA - as well as being far from fool-proof, I personally find them a significant hinderance.
Despite my best efforts, the sheer amount of spam - including a week of sustained attacks that had led me to disable comments anyway - made the decision to put aisde the lack of a commenting system in my decision to move to a static site.
Dynamic Image Re-sizing
Drupal's image styles (formerly imagecache) enabled me to upload a single image for something, and have the CMS take care of any necessary resizing. There are solutions for Jekyll, but even then it became clear that this wasn't a priority. I also found that images weren't always resized the way I wanted them, and setting the compression is something that varies according to the image - and can only, I feel, be done by eye. As such, losing this particular piece of functionality wasn't a big deal.
Other Features
Of course Drupal provides many, many other features - either in core, via third-party modules, or by writing your own. But I didn't need anything else. I didn't need to be able to switch themes, to translate content, dynamic views or a hundred and one content types. In fact, the sheer amount of unused functionality just added to the bloat.
Other Advantages
One of the problems with a CMS is that as well as having to keep a backup - preferably in source control! - of all your code, there's also the database to worry about. Indeed, with Drupal in addition to all the content being stored in the database, so too is much of the configuration (fortunately, Drupal 8 is changing this). So that's two things to worry about, and with a database that means scheduled backups. It's also much more complex to use version control with SQl sumps. With a static site, there are no such problems - the whole thing; templates, code, and content is in one place and can be safely stored away in Git.
I've reworked the design slightly, replaced all the CSS and underlying HTML, and tidied up some of the visuals.
Source-code Highlighting
I use a lot of code samples in my posts, so source-code highlighting was a must. Fortunately, Jekyll supports it by default using Pygments.
That said, there are a few steps required to make it work - the actual steps will depend on your system, and what you already have installed.
First, I had to install Pygments. I installed on a Mac, so I already had Python installed, so I simply had to do this:
sudo easy_install pygments
I also needed to ensure it was installed in my _config.yml
file:
pygments: true
The next thing I needed to do was create the css file:
pygmentize -S default -f html > css/pygments.css
And the step I forgot for a while, leading to much unecessary head-scratching - including the CSS in my layout!
At first, I struggled to get PHP code to highlight. Turns out that by default, Pygments expects <?php
tags, unless you use the startinline
option:
{{ "@{{% highlight php startinline "}}%}}
Using Pygments - which formats source-code using CSS - solved one of the problems I had with my existing site, which was that the Javascript-based solution I was using was a little tempremental. It also caused problems on mobile - though to be fair, I do find code quite difficult to read on mobiles regardless. Using CSS to format the code seems much more natural than using a plugin.
Portfolio
To use CMS parlance, Jekyll only supports one "content type", and that's blog posts. In my old site, my portfolio was comprised of a "project" content type, and I felt it would be easier to manage if I had something similar in this version of the site.
https://github.com/flatterline/jekyll-plugins
Blocks
http://stackoverflow.com/questions/8772404/jekyll-not-interpreting-markdown
In _plugins/unident.rb
:
module Jekyll
module UnindentFilter
def unindent input
input.lstrip
end
end
end
Liquid::Template.register_filter Jekyll::UnindentFilter
https://github.com/agelber/jekyll-rss
Twitter Feed
Another challenge I faced was the Twitter feed, that appears on the front page of the site.
Because it was a static site and this involved dynamic content, it made sense to explore a client-side solutio; i.e., Javascript.
Only a few months previous, this would have been a doddle - however, my website redevelopment came shortly after Twitter finally retired the old REST API - requiring developers to use OAuth, even if all you want to do is fetch a public timeline.
The problem with OAuth, of course, is that your credentials need to be kept well out of view - which makes things difficult if you're building a client-side application.
My solution - as suggested by this excellent article - was to build a simple proxy.
As such, instead of fetching the data from Twitter, my JQuery code simply needed to pass the required URL to my proxy, and then that would be responsible for making the call to Twitter, authenticating using OAuth.
The next challenge was to format the tweets. For this I found Remy Sharp's twitterlib. However, the format method was unsuitable, because it added avatars - unecessary for one person's timeline, I feel - and the format didn't fit the site. Instead, I used the method twitterlib.ify.clean
. Here's the code in full:
$(document).ready(function()
{
$.getJSON('/twitter-proxy.php?url='+encodeURIComponent('statuses/user_timeline.json?screen_name=lukaswhite&count=2&include_rts=false&exclude_replies=true'), function(d){
var html = '';
for (var i=0,len=d.length; i' + twitterlib.ify.clean(d[i].text);
html += ' — ' + twitterlib.time.datetime(d[i].created_at) + ''; // + '">' + twitterlib.time.relative(d[i].created_at) + '';
html += '';
}
html += '
';
$('#tweets').html(html);
});
});
require 'date'
module Jekyll
module NiceDate
def nice_date(input)
d = input.strftime("%e")
self.ordinalize(d.to_i) + input.strftime(" %B, %Y")
end
def ordinalize(number)
if (11..13).include?(number % 100)
"#{number}th"
else
case number % 10
when 1; "#{number}st"
when 2; "#{number}nd"
when 3; "#{number}rd"
else "#{number}th"
end
end
end
end
end
Liquid::Template.register_filter(Jekyll::NiceDate)
http://truongtx.me/2013/01/09/display-liquid-code-in-jekyll/