Given you’re a professional website designer and would like to work on some wonderful project. This project might be about designing a new website with a blog and a shop for one of your favourite customers. To get involved in this project, she asked you to design a mock-up with your ideas first and send it to her. In this article I’m going to show you how you can give away your mock-up in an easy manner without setting up a full-blown web server stack.


Short introduction to “middleman”

I really like middleman to build websites. In this article I’m going to use it, to create the mock-up. middleman is a static site generator written in Ruby and it supports a wide variety of template languages such as ERuby, Haml, Markdown or Liquid – see the this README for a full list of supported template languages. If you would like to use any of those template languages, make sure that you’ve got the required gems installed, e.g. erubis for Eruby and/or haml for Haml.

I even use middleman for some more exotic use cases like building proxy.pac-files – see this article for an introduction to proxy.pac-files – or to generate error pages for proxy servers. It’s also a great tool to serve HTML-presentations build ontop of reveal.js.

While developing a site I use the preview-server a lot. To push a new version of a site I’m responsible for, I build and upload it with capistrano-middleman.

Workflow to give away mock-up

Given that your customer has chosen you as contractor and you’ve finished the first iteration of the mock-up. To share this version of the site you and your customer need to perform the following steps shown in Fig 1. – at least in the context of this article.

Share local files

Fig. 1: Give away your mock-up to your customer

Getting started

Install “middleman”

To install middleman you need to use Rubygems. I’m going to use the latest version available of the v3-branch, v3.4.0.

gem install middleman -v 3.4.0
# => Successfully installed middleman-3.4.0
# => 1 gem installed

Create “middleman”-site

After installing middleman you setup a simple site first by using the init-command. This site is our mock-up for the time being.

middleman init new_site
# => create  new_site/Gemfile
# =>   run  bundle install from "."
# => Using i18n 0.7.0
# [...]
# => Using middleman 3.4.0
# => Bundle complete! 1 Gemfile dependency, 44 gems now installed.
# => Use `bundle show [gemname]` to see where a bundled gem is installed.
# =>   create  new_site/.gitignore
# =>   create  new_site/config.rb
# =>   create  new_site/source/index.html.erb
# =>   create  new_site/source/layouts/layout.erb
# =>   create  new_site/source/stylesheets
# =>   create  new_site/source/stylesheets/all.css
# =>   create  new_site/source/stylesheets/normalize.css
# =>   create  new_site/source/javascripts
# =>   create  new_site/source/javascripts/all.js
# =>   create  new_site/source/images
# =>   create  new_site/source/images/background.png
# =>   create  new_site/source/images/middleman.png

When the generator has finished, please switch to the newly created directory.

cd new_site

Start “middleman”-server

Before you start working on your mock-up, run middleman’s preview server. This server serves your site locally and instantly shows all changes made to the site if you enabled the LiveReload-extension.

    • Pro-Tip
  • Use tmux and spawn a new shell where you run the server. tmux is a terminal multiplexer similar to screen.
bundle exec middleman server -p 44184
# => == The Middleman is loading
# => == View your site at "http://localhost.localdomain:44184", ""
# => == Inspect your site configuration at "http://localhost.localdomain:44184/__middleman", ""

Work on mock-up

Now you can work on your mock-up and see the changes at once, if open the following URL http://localhost:44184 in your browser.

Build mock-up

Besides the preview server, it contains a command to build the static version of your site. With this command you create HyperText Markup Lanuage (HTML)-files from your templates aka views. Please run this command in another terminal.

bundle exec middleman build
# [...]
# => create  build/stylesheets/all.css
# => create  build/stylesheets/normalize.css
# [...]

Download web server

Please download the binary suitable for your own system.

curl -s \
| grep -e "browser_download_url.*linux.*" \
| cut -d : -f 2,3 \
| tr -d \" \
| xargs -I {} sh -c 'curl -L {} | tar -xzf -'

Next, please make the downloaded file an executable and place it in your build directory. If you rebuild your website, you need to move the executable to your build directory again.

chmod +x lw
mv lw ./build

Create an archive

After that, you need to create a package you can share with your customer. Please make sure, that you choose an archive-creator your customer uses as well. I prefer to use tar to create archives together with gzip – even graphical archive programs for Windows support the used algorithms.

# Create tar.gz archive
tar --xform 's/^\./2015-10-08-my-customer-her-site/' -cf 2015-10-08-my-customer-her-site.tar.gz -C build .

# Check content
tar -tf 2015-10-08-my-customer-her-site.tar.gz

An alternative would be to use zip.

# Rename directory
mv build 2015-10-08-my-customer-her-site

# Create archive
zip -r 2015-10-08-my-customer-her-site

# Check content
unzip -l 

Give away your mock-up

If you’re done with that, you can send your customer the package with the mock-up. She needs to extract the contents with one of the commands given below or use some graphical utility, and run the server.

# Extract archive
tar -xzf 2015-10-08-my-customer-her-site.tar.gz

# Alternative: Extract archive

# Switch to archive
cd 2015-10-08-my-customer-her-site

# Run server

The server will ask her for a network interface it should listen on. If she does not know anything about networking, she only needs to wait a few seconds and the server will choose to listen on localhost and opens the web site in her favourite web browser.

Wrap specific commands with “rake”

You may want to use rake – Ruby’s kind of make – to wrap project-specific commands. Personally I find it easier to remember to run rake build to build a site, than to run command_x; command_y; command_z – especially if you work on multiple very different projects in parallel. You can use this very simple Rakefile for your own project. Please don’t forget to add gem rake to your projects’s Gemfile and install the gem via bundle install.

customer_name  = 'my-customer'
site_name      = 'her-site'
date           ='%Y-%m-%d')
directory_name = "#{date}-#{customer_name}-#{site_name}"
file_name      = "#{directory_name}.tar.gz"

desc 'Default task: build site'
task :default => :build

desc 'Build site'
task :build do
  sh 'bundle exec middleman build'

desc 'Package site'
task :package => :build do
  sh "tar --xform 's/^\./#{directory_name}/' -cf #{file_name} -C build ."
  sh "tar -tf #{file_name}"

desc 'Cleanup: Remove build directory and *.tar.gz and *.zip files'
task :clean do
  rm_rf 'build/'
  rm_f Dir.glob('*.tar.gz')
  rm_f Dir.glob('*.zip')

With this Rakefile available, you can build your mock-up with the following command.

rake build

To create an archive you can send to your customer, run this command. It will run the build-task before it creates the package file.

rake package

To remove all built files including the package file, run the clean-task.

rake clean


middleman is really a great tool to build mock-ups. It doesn’t have a steep learning curve and is very easy to extend with pure Ruby, but also with rack-middlewares.

Using the lw mentioned above makes it much easier to give away a mock-up and it doesn’t require to setup a full blown web server stack which needs to be reachable by your customers.

If you find this article interesting, you might want to read this one, too. It’s about serving local directories via HTTP using the lw.

Thanks for reading!


If you found a mistake in this article or would like to contribute some content to it, please file an issue in this Git Repository


The contents of this article are put together to the best of the authors' knowledge, but it cannot be guaranteed that it's always accurate in any environment. It is up to the reader to make sure that all information found in this article, does not do any damage to the reader's working environment or wherever this information is applied to. In no event shall the authors or copyright holders be liable for any claim, damages or other liability, arising from, out of or in connection with this article. Please also note the information given on the Licences' page.