ThreeJS and Kenney Assets

The client for the browser game I want to build is going to use ThreeJS to play. I don’t know much about ThreeJS so I’m documenting what I learn here to keep a record of how this was all done.

Environment Setup

The first thing we need is a webpage to build it all on! I run a local nginx server, but for this you really just need a folder with an index.html in it. I’m going to download a few resources into this folder so we have a consistent tree, since loading assets can be complicated enough without having to figure out the “implied” setup.

Create a folder and put an index.html in it. Mine is in ~/src/threejs-obj-space for lack of a better name. In this folder, download the assets we want to use.

Put the zip file from ThreeJS into a js/ folder and extract it (it should default to three.js-master/).

Put the two asset zips into an assets/ folder and extract them. For this first pass the only stuff we really need are the Models/ folder from the 3D Space Kit and the Backgrounds/ from the 2D Space Shooter Redux.

With minimal effort you should now have all the files you need in the right place (at least to line up with how I’m going to go through this walkthrough).

Initial Code

Now we need to build out the index.html to actually render our scene.

        <style type="text/css">
                body {
                        margin: 0;
                        padding: 0;
                        background-color: #121212;

                #game {
                        width: 100%;
                        height: 100%;
                        display: block;

        <div id="game"></div>
        <script src="./js/three.js-master/build/three.js"></script>
        <script src="./js/three.js-master/examples/js/loaders/OBJLoader.js"></script>
        <script src="./js/three.js-master/examples/js/loaders/MTLLoader.js"></script>
        <script type="text/javascript">
                /* Our Code will Go Here */

This is the framework for our browser game. We create a div container called #game so we can control how it’s styled and displayed, and we include the ThreeJS files we need to render and load the assets we have.

Next we need to add a few listeners so we can properly hook up with the relevant browser events. Inside the /* Our Code will Go Here */ block, add resize, DOMContentLoaded and requestAnimationFrame listeners. We will also need a few global variables we can populate so we can reference them directly.

var scene, camera, renderer;

window.addEventListener("resize", onResize);
document.addEventListener("DOMContentLoaded", onLoaded);
let animate = () => {
let update = () => {
    //This block will be called every frame
let onResize = (event) => {
    //This block will be called when the user resizes the screen
let onLoaded = (event) => {
    //This block is called once on page load

Setting the Scene

ThreeJS needs a scene, a camera and a renderer to do anything. Inside the onLoaded function, above the animate() call, you can build these out.

var gameContainer = document.getElementById("game");

scene = new THREE.Scene();
scene.background = new THREE.Color(0x000000);

camera = new THREE.PerspectiveCamera(66, gameContainer.clientWidth / gameContainer.clientHeight, 0.1, 1000);

renderer = new THREE.WebGLRenderer();
renderer.setSize(gameContainer.clientWidth, gameContainer.clientHeight);


This will get the div that we will contain the renderer in, and then set up a ThreeJS scene.

It creates a camera with a viewing angle of 66 degrees, a near of 0.1 and a far of 1000, with an aspect ratio to match the browser window.

It sets up a renderer to match the size of the div, and attaches the renderer DOM element to the container.

But before the renderer is actually hooked up, you need to add another line, this time inside the animate() function at the bottom.

renderer.render(scene, camera);

Tada! What you’ll see is an amazing… black screen. There’s nothing in our scene! But first we need to handle resizing, since if you adjust the browser window you’ll see that the renderer doesn’t change.

Inside the onResize() function, add the following.

let gameContainer = document.getElementById("game");
camera = new THREE.PerspectiveCamera(66, gameContainer.clientWidth / gameContainer.clientHeight, 0.1, 1000);
renderer.setSize(gameContainer.clientWidth, gameContainer.clientHeight);

This will recreate (and replace) our perspective camera using the new browser window dimensions, and adjust the renderer to the new dimensions as well.

Setting the Scene

Now that we have the basics in place to display something, we need to add something to display. I started by loading in a tiled texture plane and an ambient light so I could see it. Inside the onLoaded function, add:

let ambientLight = new THREE.AmbientLight(0xffffff);
ambientLight.intensity = 0.8;

let starfieldTexture = new THREE.TextureLoader().load('./assets/Backgrounds/blue.png');
starfieldTexture.wrapS = THREE.RepeatWrapping;
starfieldTexture.wrapT = THREE.RepeatWrapping;
starfieldTexture.repeat.set(20, 20);

let geometry = new THREE.PlaneGeometry(500, 500, 256, 256);
let material = new THREE.MeshLambertMaterial({map: starfieldTexture, color: 0xffffff});

let starfield = new THREE.Mesh(geometry, material);
starfield.position.z = -10;

Finally! The fruits of our labor:

… a dimly lit image. How exciting. It’s pretty neat though, considering now you could play around with the lighting intensity (anywhere from 0 – 1) or the background texture we’re loading (black.png and purple.png being other options available).

My favorite thing to do now is get a different perspective. Literally!

We have some duplication in the code; we create the camera twice in the load and resize. Instead, refactor out that creation to a separate function and call it in both places.

let buildCamera = () => {
    let gameContainer = document.getElementById("game");
    camera = new THREE.PerspectiveCamera(66, gameContainer.clientWidth / gameContainer.clientHeight, 0.1, 1000);

Now any changes you want to make to the camera can be done in the shared function. Let’s change the position and viewing angle so we get a different look at our starfield plane. Put these lines inside the buildCamera()function at the bottom.

camera.position.y = -25;
camera.position.x = -25;
camera.position.z = 50;
camera.up = new THREE.Vector3(1, 1, 0);
camera.lookAt(new THREE.Vector3(0, 0, 0);

This moves the camera upward (Z is up in ThreeJS) by 50 units, and left and down by -25 each. Then we tell the camera how to orient itself and look at the center of the plane. (0, 0, 0)

Look! Now we see the starfield at an angle. Thrilling! But wait, there’s more!

A Spacecraft Appears

This next part is complicated because it adds in a ton of things really fast. Since it’s all unified but complex, this is a perfect candidate for a function. First, add a function call inside the onLoaded(), below where we add the starfield to the scene.


let starfield = new THREE.Mesh(geometry, material);
starfield.position.z = -10;


Now, make a function called addSpaceCraft and we’ll add in the Material and Object loader. Loaders have some additional functions that can provide extra information in case something goes wrong during this process, so we’ll write those to output their status so debugging is easier.

let onProgress = (data) => {
    console.log("onProgress", data);

let onError = (error) => {
    console.error("onError", error);

let addSpaceCraft = (scene) => {
    let materialLoader = new THREE.MTLLoader();
    let objectLoader = new THREE.OBJLoader();
    materialLoader.load('./assets/Models/spaceCraft1.mtl', (materials) => {
        objectLoader.load('./assets/Models/spaceCraft1.obj', (object) => {
            object.rotation.x = 90;
        }, onProgress, onError);
    }, onProgress, onError);

Now reload your page and take a look:

A spacecraft! Incredible! If you don’t see a ship at this point, check your browser console for some of those helpful log messages we put in. Things that might fail here are bad material data, bad object data, incorrect paths to the assets or even typos in the callback function that aren’t immediately apparent.

At this point, you have enough of the basics to be able to use the Kenny assets to build something out in ThreeJS.

But I’m not finished yet. Let’s add some better lighting and maybe a bit of a float effect on the spacecraft.

First, we need to save off the spacecraft so we can access it and manipulate it later. Create another few global variables at the top.

var scene, camera, renderer;

var spaceCraft;
var oscillator = 0;


Near the line where we add the spacecraft object to the stage, save the object into our new spaceCraft global.

            object.rotation.x = 90;

            spaceCraft = object;

        }, onProgress, onError);

For the floating effect, we’ll use a rudimentary oscillator in the update() function.

let update = () => {
    oscillator += 1;
    oscillator %= 360;

    if(spaceCraft) {
        spaceCraft.position.z = Math.sin(oscillator * Math.PI / 180);
        spaceCraft.rotation.z = Math.cos(oscillator * Math.PI / 180) / 8;

This will result in the spacecraft gently moving up and down while rocking back and forth. But the model itself still looks pretty flat, so let’s add in some lighting and shadows.

In the onLoaded() function, near where we added the ambient light, add a new function called addSpotLight.

    let ambientLight = new THREE.AmbientLight(0xffffff);
    ambientLight.intensity = 0.8;


Inside this new function we will add a focused spot light so that the spacecraft material can be directionally illuminated. This will make the ship look a lot less flat and a lot more shiny.

let addSpotLight = (scene) => {
    spotLight = new THREE.SpotLight(0xffffff);
    spotLight.position.set(0, 0, 100);

    spotLight.angle = 0.18;
    spotLight.penumbra = 1;
    spotLight.intensity = 0.2;

Now that is an awesome looking spaceship.

I hope this walkthrough can help others as much as it helped me to write it out. If you have any issues or comments, please let me know! I love hearing about game developers learning new things. Especially if they’re me!

Adventures in Game Development

So I made a resolution to work on and finish a game this year. I’ve been a developer for ages and I have dozens of half-finished projects, but without setting any goals I haven’t really accomplished anything.

I spent the first month of 2020 researching the tools I think I want to use and planning out what kind of a game I want to build. To help me stay focused and motivated, I’m going to document my research and progress here.

Game Idea

I keep coming around to a few common themes while building my game prototypes. I really like the idea of a 2D space game. Something maybe top-down or isometric. I absolutely want it to be multiplayer and browser-based, so anyone can join and play.

I like the Minecraft style procedural world with strict progression, so I’m envisioning an “infinite” space environment where players can jump to other sectors to explore.

Stars, planets, space stations and asteroid fields would all be candidates for appearing in sectors, allowing players to mine, trade, craft, chat and fight.


There are a few things I want to learn along the way. I think I’ve settled on a ThreeJS client, and a dotnetcore backend. I’m going to use for the assets while developing, and fake out everything else using primitive shapes or textures.

The Beginning

I have a lot to learn as well as a lot to build, and it’s not like I’m quitting my day job to do it.

I’m going to start by building a dotnet core server to manage game state. Basically, a chat server for now. Wish me luck!

GNU Screen Configuration and User Guide

If you’re a command-line user, there’s a good chance you’ve come across the best way to handle multiple sessions through a terminal, screen!

It’s a simple, powerful tool that you can get set up using either

$ sudo apt install screen


$ brew install screen

but it’s a little cryptic to use! First, I’d suggest setting it up so you can make it look nicer and be a bit more informative.

In your home directory (~/) create (or edit) your .screenrc file. In it, put the following configurations:

startup_message off
attrcolor b ".I"
term xterm-256color
defscrollback 30000
hardstatus alwayslastline
hardstatus string '%H %= %t:Screen %n%f %= %Y-%m-%d %c'

This will allow for things like bold text, colors in the terminal, a very long scrollback and an informative status bar across the bottom of the screen.

Now just run

$ screen

in your terminal and you’ll jump into a created screen! But why bother with this when logging in works just as well? Screen has a ton of useful features.

First, let’s go with the basics. Press Ctrl a and then c to create and jump to a new screen. If you’re using the screen configuration we set earlier, the only change you’ll see right away is that the Screen 1 at the bottom is being displayed instead of Screen 0. To move between these screens, type

Ctrl a n to move to the next screen (it cycles around) or

Ctrl a p to move to the previous screen.

You can give each of these screens it’s own title to make it easier to notice what screen you might be looking at.

Ctrl a Shift A will open a prompt “Set window title to:” and will allow you to edit the title text there.

Screen is also able to run in the background. This is useful if you want to keep the same session on a remote machine but log in from different locations.

Ctrl a d will put the current screen session into a “detached” state. The processes inside that screen session will continue to run (poor-man’s service) and you can see what sessions are running by typing

$ screen -ls

If there is only one detached session, you can easily run

$ screen -r and immediately reattach to that screen session. If there are multiple detached screens, you’ll have to specify the screen session name or screen id.

There is a screen on:
29529.ttys002.LAPTOP-1083 (Detached)

$ screen -r 29529

Screen has a lot more capabilities than what I covered here, but you can see a list of all of the commands and shortcuts while inside of a screen session if you type

Ctrl a : and then help

Command key:  ^A   Literal ^A:  a
   break       ^B b
   clear       C
   colon       :
   copy        ^[ [
   detach      ^D d
   digraph     ^V
   displays    *
   dumptermcap .
   fit         F
   flow        ^F f
   focus       ^I
   hardcopy    h   
   help        ?
   history     { }
   info        i
   kill        ^K k
   lastmsg     ^M m
   license     ,
   lockscreen  ^X x
   log         H
   meta        a
   monitor     M
   next        ^@ ^N sp n
   number      N
   only        Q
   other       ^A
   pow_break   B
   pow_detach  D
   prev        ^H ^P p ^?
   quit        ^\
   readbuf     <
   redisplay   ^L l
   remove      X
   removebuf   =
   reset       Z
   screen      ^C c
   select      '
   silence     _
   split       S
   suspend     ^Z z
   time        ^T t
   title       A
   vbell       ^G
   version     v
   width       W
   windows     ^W w
   wrap        ^R r
   writebuf    >
   xoff        ^S s
   xon         ^Q q
   ^]  paste .
   "   windowlist -b
   select -
   0   select 0
   1   select 1
   2   select 2
   3   select 3
   4   select 4
   5   select 5
   6   select 6
   7   select 7
   8   select 8
   9   select 9
   ]    paste . 

Enjoy using screen!

How to set up C# dotnet core development from scratch on Ubuntu 18.04

First things first: you need to install dotnet core on your computer. You can find the SDK download and instructions here:

To allow Aptitude to install Microsoft packages, you’ll have to add the Microsoft Certificate Key. Luckily, Microsoft has provided this in a convenient package.

wget -q
sudo dpkg -i packages-microsoft-prod.deb

Once you have the key, you’ll need to add the repository and HTTPS support.

sudo add-apt-repository universe
sudo apt install apt-transport-https
sudo apt update

Finally, you’re ready to install dotnet core!

sudo apt install dotnet-sdk-2.2

The next thing you’ll need to do is set up your IDE. you could use vi or nano, but to make things consistent and simple, I use VS Code. You’ll have to download the .deb package from here:

Direct Link:


Then you just need to install it! (your version number might be different)

sudo dpkg -i code_1.31.1-1549938243_amd64.deb

Once you’ve installed the editor, run it and add the C# extension. You can find it here:

copy the quick code line

ext install ms-vscode.csharp

and in VS Code press Ctrl+P and paste the line in to install.

Now you’re set up to build dotnet core applications and libraries on Ubuntu! For what you can do with this, please see my post on [How to set up a dotnet core REST API with Dapper and xunit]! (coming soon)

Learning Ansible like a Command Line addict (Part 2)

Please see part 1

Everything I’ve read about Ansible talks about these big fancy “playbooks” but all I know how to do is run a ping from the command line to check if my servers exist. Do I have to copy an existing playbook and hope it does what I want?

Yea, forget that! Let’s try running something simple, like a file copy. Remember, I set this up as my jenkins user, but whatever user you’re using, log in as them to do the next parts.

First, we need a file to copy. I started with a dummy file in my home directory, hello.txt and some text inside “hello ansible!” So to run a copy command from ansible, you have to type:

ansible -m copy -a "src=./hello.txt dest=./" webservers

And you get a ton of awesome output!

jenkins@deploy:~$ ansible -m copy -a "src=./hello.txt dest=./" webservers
web02 | SUCCESS => {
 "changed": true, 
 "checksum": "af53119865a6f135b4ab851cb2b580cdc8e9f075", 
 "dest": "./hello.txt", 
 "gid": 1001, 
 "group": "deploy", 
 "md5sum": "0b2f7c2ec4095f9b8466c0913f1af3f3", 
 "mode": "0644", 
 "owner": "deploy", 
 "size": 15, 
 "src": "/home/deploy/.ansible/tmp/ansible-tmp-1497728808.43-244137364817946/source", 
 "state": "file", 
 "uid": 1001
web01 | SUCCESS => {
 "changed": true, 
 "checksum": "af53119865a6f135b4ab851cb2b580cdc8e9f075", 
 "dest": "./hello.txt", 
 "gid": 1001, 
 "group": "deploy", 
 "md5sum": "0b2f7c2ec4095f9b8466c0913f1af3f3", 
 "mode": "0644", 
 "owner": "deploy", 
 "size": 15, 
 "src": "/home/deploy/.ansible/tmp/ansible-tmp-1497728808.42-136193633452143/source", 
 "state": "file", 
 "uid": 1001

You’ll see on each of the webservers that there is now a hello.txt file in the deploy user’s home directory. Sweet! But a copy command is pretty slow when you’re dealing with a website’s worth of files. Maybe we can use rsync to speed this process up a bit?

NOTE: I did not have rsync on any of the servers in question here, so stuff blew up and I had to install it. sudo apt-get install rsync before you suffer the same fate as me!

To test, create a directory of project files (test-directory was mine) and move the hello.txt into it. I created a few other files in there too just to see how it worked. Then just run

ansible -m synchronize -a "src=./test-directory/ dest=./ archive=yes rsync_opts=--exclude=.git" webservers

And this will use rsync to copy the contents of the test-directory into the home directory of the deploy user on each of the servers.

Now we have a pretty decent way to deploy versioned releases of the code to our webservers. However, we’ll need a way to tell our webserver where the new directory is. I use symlinks which makes it simple. Just point the Apache or nginx config file at the symlink, and when you do a release you can swap it out. Often times you don’t even need to restart the server.

Here’s the list of the commands I used on my Jenkins CI deploy tool.

ansible -m file -a "path=project1/${BUILD_TAG} state=directory" webservers
ansible -m synchronize -a "src=./ dest=project1/${BUILD_TAG}/ archive=yes rsync_opts=--exclude=.git" webservers
ansible -m file -a "path=project1-live state=absent" webservers
ansible -m file -a "src=project1/${BUILD_TAG} dest=project1-live state=link" webservers

This worked pretty awesome… at least until I deployed 20 times and ran out of disk space. I wasn’t cleaning up any of my old builds! I found a helpful but non-functioning answer on Stack Overflow ( and I hit a wall. I couldn’t figure out how to run “with_items” without building out a playbook.

I struggled for a few days, but it suddenly clicked: I know enough about Ansible now to be able to build a playbook that does exactly what I want.

With those previous commands, I created an identical playbook in the jenkins home directory.

- hosts: webservers
 - name: create versioned directory
 file: path=project1/{{ build_tag }} state=directory

- name: sync files to folder
 synchronize: src=./ dest=project1/{{ build_tag }}/ archive=yes rsync_opts=--exclude.git

- name: delete symlink
 file: path=project1-live state=absent

- name: link new site
 file: src=project1/${{ build_tag }} dest=project1-live state=link

Then in Jenkins I just had to run:

ansible-playbook ${JENKINS_HOME}/project1-playbook.yml --extra-vars="build_tag=${BUILD_TAG}"

And it does exactly the same thing as before!

Now I can make some modifications to this playbook to clean up old deploy versions, and we should be good to go. Here’s my final playbook and Jenkins build command.

Created an “ansible-playbooks” directory in jenkins home, and then added the file ~jenkins/ansible-playbooks/webdeploy-playbook.yml

- hosts: "{{ server }}"
 - name: create versioned directory
 file: path={{ deploy_folder }}/{{ build_tag }} state=directory

- name: sync files to folder
 synchronize: src={{ workspace }} dest={{ deploy_folder }}/{{ build_tag }}/ archive=yes rsync_opts=--exclude=.git

- name: delete symlink
 file: path={{ symlink_name }} state=absent

- name: link new site
 file: src={{ deploy_folder }}/{{ build_tag }} dest={{ symlink_name }} state=link

- name: get list of old releases
 shell: "ls -1r {{ deploy_folder }} | tail -n +{{ releases_to_keep | int + 1 }}"
 register: ls_output

- name: delete old versions
 file: name={{ deploy_folder }}/{{ item }} state=absent
 with_items: "{{ ls_output.stdout_lines }}"

And put this in as the build step for the jenkins project.

ansible-playbook ${JENKINS_HOME}/ansible-playbooks/webdeploy-playbook.yml --extra-vars="build_tag=${BUILD_TAG} workspace=${WORKSPACE} deploy_folder=project1 symlink_name=project1-live server=webservers releases_to_keep=3"

This was a pretty tough way to go about learning it, but hopefully this helps out my fellow command line junkies trying to learn Ansible playbooks.

Learning Ansible like a Command Line addict

I’ve always been hindered by my ability to deploy code using existing tools, and often times I lean too heavily on my ability as a programmer to solve this problem. As a result, I’ve written multiple deployment systems from scratch, and can’t use common tools as a result. So I’ve set out to learn Ansible, but I’m gonna do it in the most backwards way possible.

First, we have to get Ansible ( I have a Jenkins build server that compiles and packages artifacts, so it makes sense that it would be able to deploy those packages when approved. Luckily, Ansible provides a nice Aptitude package repo.

Add the file /etc/apt/sources.list.d/ansible.list​ with the contents:

deb trusty main

Then run these commands:

sudo apt-key adv --keyserver --recv-keys 93C4A3FD7BB9C367
sudo apt-get update
sudo apt-get install ansible

And now you should have Ansible installed. So… now what?

Well, I wanted to use this to deploy to remote servers via SSH. So let’s try adding some servers.

Edit /etc/ansible/hosts and add this at the bottom (obviously change for your server needs)

web01 ansible_ssh_host=
web02 ansible_ssh_host=

And we need to add a username so that we have a deploy user with the appropriate access. Add a file /etc/ansible/group_vars/webservers​ and give it the following contents

ansible_ssh_user: deploy

NOTE: This config file is formatted YAML. Those three dashes at the top are actually pretty critical. Don’t miss them!

This will make all connections use the deploy user, regardless of which user on the deploy server is running the command. Well, that’s cool. So now what? Let’s test it!

ansible -m ping webservers

Should fire off a command to each server listed under the webservers group, and return back if that server responds correctly.

midas@deploy:~$ ansible -m ping webservers
The authenticity of host ' (' can't be established.
ECDSA key fingerprint is ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff.
Are you sure you want to continue connecting (yes/no)? web01 | UNREACHABLE! => {
 "changed": false, 
 "msg": "Failed to connect to the host via ssh: Permission denied (publickey).\r\n", 
 "unreachable": true
web02 | UNREACHABLE! => {
 "changed": false, 
 "msg": "Failed to connect to the host via ssh: Warning: Permanently added '' (ECDSA) to the list of known hosts.\r\nPermission denied (publickey).\r\n", 
 "unreachable": true

Oh god what a mess. It looks like we forgot a critical step; adding a user and ssh key to each of the web servers we are trying to deploy to. Since I want my jenkins install to be able to do this, I’ll switch over to the jenkins user and generate a key pair for this account.

sudo su - jenkins
ssh-keygen -t rsa -b 4096
cat ~/.ssh/

Now that I’ve got a key, I need to create a deploy user on each of my target servers and add the jenkins public key to the authorized_keys file. (This step is left as an exercise for the reader). Now we just need to test it, so from the jenkins account, run

ssh deploy@ "echo hello"
ssh deploy@ "echo hello"

and make sure you accept the ECDSA key fingerprint for the first connection. Awesome!

So now from the jenkins account, let’s run that ping command again.

jenkins@deploy:~$ ansible -m ping webservers
web02 | SUCCESS => {
 "changed": false, 
 "ping": "pong"
web01 | SUCCESS => {
 "changed": false, 
 "ping": "pong"

Hooray! But that’s hardly useful, so let’s get cracking at something meaningful. Part two, coming soon!

Update: You can find part 2 here


Tiling web assets (sprites) using montage

I’m updating a few sites to include some social media links, but finding nice icons is tough. There are lots of free icon sets on DeviantArt, and one I found is pretty great!

Unfortunately, the assets all come in separate files. This makes it easy to use right away, but if you want to support all of them, it’s a little inefficient. So I decided to combine the images using a linux tool called montage.

montage -adjoin *.png -background none -size +42+42 -geometry +1+1 montage.png

The images I have are 42px by 42px and transparent. This line will tile the images inside the folder, assuming all the images are +42+42 and leaving a 1px by 1px gap between them.

This is all well and good, now I’ve got a nicely tiled image:

Transparent with white icons. Not easy to see…

But how do I use this? Sprites! In the HTML I want something simple so it’s easy for me to add or adjust the icon.

<a class="social-media wordpress" href=""></a>

Then I just add in a a bit of css styling…

.social-media {
    width: 42px;
    height: 42px;
    display: inline-block;
    background-image: url('../images/social_media_sprite.png');
.social-media.wordpress { background-position: -177px -221px;}

And presto! I can slice out any icon from the spritesheet and add it to my page with a simple classname.

The entire spritesheet and css file can be found here.

Sitecore 8.2 Custom Error Page

I spent a long time googling for an answer to this, and never really found one. I talked to my friend Noel who showed me the way his team implemented a custom error page for their Sitecore site, and I’m documenting it here.

I wanted a single, shared error page that was editable inside of the Sitecore Content Editor that would show up for any 404 or 500 error page (or any error page).

First, create a rich text component for what you want to display on this error page.

Screen Shot 2017-04-24 at 09.02.48

I put this under a “Global Content” section, and copied the item path (which we’ll use later as a data source)

Then in the “Home” section of your site, add a page named “error”.

Screen Shot 2017-04-24 at 09.01.18

Edit it’s presentation details and add a rich text rendering (like the component you created earlier) and set it’s placeholder to ‘content’ and it’s data source to the path of your Rich Text Component.

Screen Shot 2017-04-24 at 09.01.43

Screen Shot 2017-04-24 at 09.02.04

Screen Shot 2017-04-24 at 09.02.17

Save and publish, and you should now have an /error page available on your site.

In the Sitecore configuration files, you’ll have to add or edit some settings.

In /App_Config/Sitecore.config, there are several setting fields that will need to be changed.

<setting name="LayoutNotFoundUrl" value="/error" />
<setting name="LinkItemNotFoundUrl" value="/error" />
<setting name="ItemNotFoundUrl" value="/error" />
<setting name="NoAccessUrl" value="/error" />
<setting name="ErrorPage" value="/error" />

If you require specific error messages for each page, just change these fields to point to whatever page you want inside Sitecore.

It’s that simple! No code changes necessary (like most of the google results I found while trying to learn how to do this)

Using DotNet Core on Ubuntu to build an MVC website

I recently had some time to poke around outside of my normal comfort zone of open-source languages and try some new stuff from the Microsoft side of things. I was pleasantly surprised at how nice it is over the fence!

So the first thing I needed to do was install dotnet[1] and a dotnet-friendly editor[2].

I am on Ubuntu 16.04, so I had to add the repository to my aptitude source list.

sudo sh -c 'echo "deb [arch=amd64] xenial main" > /etc/apt/sources.list.d/dotnetdev.list'
sudo apt-key adv --keyserver hkp:// --recv-keys 417A0893
sudo apt-get update

It’s a little complicated, but it makes installing and maintaining versions that much easier. To install dotnet core, it was as easy as

sudo apt-get install dotnet-dev-1.0.1

Bam! dotnet core installed! Oh wait. Ok, so things didn’t go perfectly, and I had to do some manual installs to get it actually working.

sudo apt-get -f install
sudo apt-get install liburcu4 liblttng-ust0 dotnet-dev-1.0.1

Next I needed an editor, and I figured Visual Studio Code was the right choice. So I added the repository.

curl | gpg --dearmor > microsoft.gpg
sudo mv microsoft.gpg /etc/apt/trusted.gpg.d/microsoft.gpg
sudo sh -c 'echo "deb [arch=amd64] stable main" > /etc/apt/sources.list.d/vscode.list'
sudo apt-get update

Which then made installing it just as simple.

sudo apt-get install code 

The next step was to get the environment set up to run C# application code nicely. So I opened Visual Studio Code and pressed Ctrl+Shift+P and typed ext install and chose to install the C# plugin from Microsoft.

Still with me? That’s it. The environment was really easy to set up. I decided to create a new MVC project from the command line (since I know it a lot better than my new editor) so I created a folder in my ~/src/ directory called the incredibly original dotnet_mvc.

mkdir -p ~/src/dotnet_mvc
cd ~/src/dotnet_mvc

To create a new default MVC project, use

dotnet new mvc

This will create essentially a “Hello World” type web application using Kestrel, a web server for ASP.NET.

The dependencies it has aren’t all automatically included, but a simple

dotnet restore

fixes those issues. (This is also managed by VS Code so if you do it in the IDE, there’s just a friendly popup asking you if you want to run the Restore action.)

Now we can actually start messing around inside the application! In Visual Studio Code, click File > Open Directory and navigate to the dotnet_mvc project folder. By default you have a HomeController.cs file inside the Controllers/ directory, and a Startup.cs file in the root which defines the server settings and url routes.

So proof of concept built, let’s see if it runs! Click the “Debug” icon on the left and press the little green arrow at the top of the screen. The project will be built and run, and VS Code will open your default browser to localhost:5000 where you will find a default web application.


Check back in next time when I add a new route, controller and support for a JSON REST API.

Starbound as a Service (SaaS)

Ever since the release of Starbound 1.0 I’ve dove back into it. I love the procedurally generated worlds, the platformer boss fights and, of course, playing with others.

Starbound comes with a Linux client AND a dedicated multiplayer server, so it’s basically a given that I would be hosting one. Now, you can run it through Steam, but that gets cumbersome if you want to play, too. So I used steamcmd and a custom systemd file so I can start and stop the server automatically, or with a really intuitive (for a debian or Ubuntu user) command:

$ sudo service starbound start|stop|status

How did I do it? Simple! [1]

Install steamcmd

I usually put custom installed stuff in my /opt directory, so I created a /opt/steamcmd directory and pulled down the steamcmd binary from the Steam CDN.

You can find all of these steps on the starbounder wiki site although it’s a little dated (it’s from before they had a 64bit linux client).

cd /opt
sudo mkdir steamcmd
sudo adduser steam
sudo chown steam:steam steamcmd
su - steam
cd steamcmd
tar -zxvf steamcmd_linux.tar.gz

By the end of this, you’ll have a useable steamcmd install, but with no games installed. So obviously, the next step is to

Install Starbound

In the terminal, run


Which will put you inside the steamcmd prompt steam>

force_install_dir starbound
app_update 211820

This bit will take a while since it has to download all of the files, so open a new terminal and

Add a systemd config file

in /etc/systemd/system create a file called starbound.service and put this information in it.




The two fields you might need to customize here are the WorkingDirectory and the ExeStart paths. Since I have everything installed in /opt/steamcmd/starbound these paths work for me.

Once the starbound steamcmd is installed, you can use

sudo service starbound start

to begin hosting a playable world! If you intend to host over a LAN or even on the internet, you’ll need to make a slight change to the starbound.config file in /opt/steamcmd/starbound/giraffe_storage directory.

Just change these three lines

"gameServerBind" : "::",
"queryServerBind" : "::",
"rconServerBind" : "::",

to your LAN IP. For instance, when I run

ip addr

It shows my IP as So my config file says

"gameServerBind" : "",
"queryServerBind" : "",
"rconServerBind" : "",

Happy exploring!