Starting a blog with Sculpin on Laravel Forge
This is a series of posts on Laravel Forge.
!Warning: This post is over a year old. I don't always update old posts with new information, so some of this information may be out of date.
I recently switched The Five Minute Geek Show's web site over to Sculpin for its content management. If you're not familiar, Sculpin is a static site generator, which means I have my content and template in markdown files, which I then run a script over, and the script generates static HTML files, which I then deploy to my server. This means there's no PHP or Ruby or Python or anything serving my files; by the time they hit my web server, they're just flat HTML.
Sculpin itself has pretty great documentation, but I still wanted to provide a run-down of the steps I took to get the Five Minute Geek Show's site running in Sculpin and hosted on Forge.
Getting Sculpin running
It's best to check out the Sculpin Quick Start to get up and running, but in short, here are the commands I ran:
$ curl -O https://download.sculpin.io/sculpin.phar
$ chmod +x sculpin.phar
$ mv sculpin.phar ~/usr/local/bin/sculpin
$ cd ~/Sites
$ git clone https://github.com/sculpin/sculpin-blog-skeleton.git fiveMinuteGeekShowBlog
$ cd fiveMinuteGeekShowBlog
$ sculpin install
$ sculpin generate --watch --server
$ cd source/_posts
# Edit whichever files
# Preview in browser at http://localhost:8000/
$ sculpin generate --env=prod
$ rsync -avze 'ssh -p 999' output_prod/ user@example.com:public_html
If you're new to Sculpin or static site generators in general, please read on. If you're not, please skip to the "Sculpin on Forge" section.
Here are the steps listed above, broken down:
1. Install Sculpin
$ curl -O https://download.sculpin.io/sculpin.phar
$ chmod +x sculpin.phar
$ mv sculpin.phar ~/usr/local/bin/sculpin
Our first lines are downloading the sculpin.phar
executable file to our computer, marking it as executable, and then moving it into our bin
directory so it's in our PATH
and will be runnable from anywhere on the system (via the Terminal.) It's now installed "globally," meaning it's not just connected to a particular folder or project.
This step has been run successfully if you can spin up a new Terminal window, navigate anywhere on your computer, and run sculpin
and get a positive response. If not, the issue is likely with your PATH
.
2. Download a template
$ cd ~/Sites
$ git clone https://github.com/sculpin/sculpin-blog-skeleton.git fiveMinuteGeekShowBlog
$ cd fiveMinuteGeekShowBlog
Sculpin can be used for a lot more than blogs, but the sculpin-blog-skeleton
makes it really easy to get up and running with a Sculpin-based blog. So, we're now cloning a copy of the of the blog skeleton repository into where we keep our sites (I use ~/Sites
).
3. Install Sculpin dependencies locally
$ sculpin install
sculpin install
is basically a wrapper around composer install
, so we're just installing our dependencies locally to this project.
4. Generate a watching server
$ sculpin generate --watch --server
sculpin generate
scans the source
directory and generates static files in output_dev
or, if the --env ENVNAMEHERE
flag is used, the output_ENVNAMEHERE
folder.
NOTE: Usually you don't ever pass a
--env
flag. Sculpin defaults to --env=dev, and it automatically serves its previews from theoutput_dev
folder, so you don't have to worry about that. And for prod, usually your publish script will have--env=prod
andoutput_prod
baked into them, so you won't have to think about this at all unless you're writing a publish script.
Adding the --watch
flag sets it as a long-running script (like Grunt or Gulp) that watches the filesystem and auto-generates on any changes.
Adding the --server
flag spins up a server at http://localhost:8000/ (you can specify the port with --port=8090
) for you to check your changes at.
5. Edit files
Now you can edit, add, or delete files from anywhere in the source
directory. Blog posts, in this skeleton, go in source/_posts
. Check out app/config/sculpin_kernel.yml
to set the URL structure for your content types, or app/config/sculpin_site.yml
to change site-wide variables.
For a great example (it's the one I used) of how to modify that skeleton for Podcast web sites, check out Adam Wathan's Full-Stack Radio repository.
6. Sync up
$ rsync -avze 'ssh -p 999' output_prod/ user@example.com:public_html
The default prescribed method to move your files from your local site to your remote server is not git; you're saving your source in git, but you're not actually hooking up the production web site to your git repo. Rather, you're using this last line to copy the files from the output_prod
folder of your local install up to the public_html
(or whatever) folder on your production server.
Breaking down the rsync command
rsync -avze 'ssh -p 999'
set the basic context, flags, and permissions for this rsync session.
output_prod/
shows which directory to copy from.
user@example.com
is your username and domain for your remote server.
public_html
is the remote directly it should be uploading to.
Sculpin on Forge
If you've ever used Forge before, you know it's absurdly easy to spin up a server and hook it up to a Github repo.
So, I created a new Github repo--this is not the only way to do it, but it is definitely one option--named FiveMinuteGeekShowPublic--and made it empty. I then cloned it to my ~/Sites
directory.
I spun up a new site on Forge on a Linode box for http://fiveminutegeekshow.com/
, told it to pull its data from this new repo, and then set it to "Quick Deploy" (meaning, every time I push to the master branch, it runs a certain script).
I edited the Quick Deploy script to be appropriate for this site:
cd /home/forge/fiveminutegeekshow.com
git pull origin master
Then I was ready to go. I set up a publish script in my FiveMinuteGeekShow
repo that generates production HTML, copies the files from Sculpin's output_prod
folder over to my local FiveMinuteGeekShowPublic
folder, and then git commits and pushes.
I ran chmod +x publish.sh
, and now I publish my blog by navigating to the fiveMinuteGeekShow
directory and typing ./publish.sh
.
Cleaner publishing
As you can tell, my publish script relies on a certain directory structure on my local machine, which is quick and easy but also a bit hacky.
You can see in Sculpin's default documentation that you can also just use rsync
to copy the files directly up to your server. Check out the notes above of how your rsync command is actually structured.
You could do this with Forge. Just don't sync a Github repo, and use the credentials you were emailed when you first spun up this Forge server to set up the rsync to copy your output_prod
folder up to the remote server. Same deal, and it doesn't rely on Git.
404 and nginx config
I have to thank Adam Wathan for this one. I tried to get a custom 404 page by setting error_page 404 /404/index.html
in my Forge nginx configuration and discovered that it wouldn't work.
Adam helped me realize that Forge's default references to all of the .php
files would override it ever hitting the 404 page, so he helped me clean up my nginx config. It ended up looking like this:
server {
listen 80;
server_name fiveminutegeekshow.com;
root /home/forge/fiveminutegeekshow.com;
error_page 404 /404/index.html;
# FORGE SSL (DO NOT REMOVE!)
# ssl_certificate;
# ssl_certificate_key;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
index index.html index.htm;
charset utf-8;
location = /favicon.ico { access_log off; log_not_found off; }
location = /robots.txt { access_log off; log_not_found off; }
access_log off;
error_log /var/log/nginx/fiveminutegeekshow.com-error.log error;
location ~ /\.ht {
deny all;
}
}
Now, any time someone visits a bad route, they'll get the 404 page.
Conch shell lusion
As you can see, wrapping your head around Sculpin--and static site generators in general--can take a minute, but once you get it, it's actually a very simple process, and hosting it on Forge is surprisingly simple.
Using Github pages or Heroku are also great options, but if you're already in the Forge space--or if you want to eventually add other functionality to the site other than just the static files being generated by Sculpin--Sculpin + Forge is a great combination.
Comments? I'm @stauffermatt on Twitter
Tags: forge • sculpin • fiveMinuteGeekShow
This is part of a series of posts on Laravel Forge:
-
May 15, 2014 | laravel, forge
-
May 16, 2014 | forge, laravel, papertrail
-
May 19, 2014 | laravel, forge, environment
-
May 23, 2014 | laravel, forge, queue, beanstalkd
-
Jun 2, 2014 | laravel, forge, cron
-
Jun 2, 2014 | forge, laravel, ssl
-
Jun 17, 2014 | forge, htpasswd, nginx
-
Jun 23, 2014 | laravel, forge, subdomains
-
Jul 9, 2014 | forge, laravel, recipes
-
Jul 25, 2014 | laravel, forge, aws, hosting
-
Sep 17, 2014 | laravel, forge
-
Sep 24, 2014 | laravel, forge
-
Sep 25, 2014 | laravel, forge, recipes
-
Dec 24, 2014 | forge, sculpin, fiveMinuteGeekShow
-
Dec 29, 2014 | laravel, forge, craft