A quick disclaimer: This tutorial assumes a working knowledge of the Linux command Line, access to a text editor, and a basic programming background. None of the steps outlined here are guaranteed to work on Mac or Windows machines as I do not have enough experience working in those environments. Also, I am not responsible if you make a mistake and blow up your machine.

Why?

I personally find it to be a fun exercise to try building small projects with new packages and libraries I’ve never used before. It’s even more fun to combine libraries into a stack that I haven’t seen before.

What we will be Building

We will build a simple movie database from scratch. The reasons for this are listed in the Outlining our Application section below.

Stuff we’ll be using:

Python 3

I’ve been a Python fanboy ever since I started programming. I find it to be a great language for back-end web development. It’s flexible and has pleasant syntax.

Hug

Hug is library designed to help developers create Web Applications, Command line interfaces, and all sorts of other useful abstractions. We will be using it’s web API functionality.

MongoDb

MongoDb has gotten a lot of flack over the years for lack of security. In reality, this isn’t the case. The real issue is that Mongo does not come with any security configuration out-of-the-box! This means that when a Mongo-backed application is deployed into production, you need to ensure you have configured access control. Otherwise, any old joe-schmoe can do whatever they want to your data. Mongo security configuration is out of the scope of this tutorial, but you can read more about it here.

We will be using mongo for our project because I haven’t seen it paired with Python out in the wild all that often. Plus, working without rigorous schemas can be refreshing sometimes.

Pymongo package

Pymongo is a driver for MongoDb. It will allow us to interface with Mongo from our Python application. There are some ODMs(Object Document Mappers) out there, but I find them to be a bit overkill for working with Mongo. YMMV.

Marshmallow package

We will be using the Python Marshmallow package for JSON serialization. It will also help us enforce data validation for our Mongo documents.

Python Virtualenv

A Python Virtualenv is exactly what it sounds like. It allows us to create isolated Python runtime environments so we don’t accidentally polute or break our system level Python package.

Vue.js

Vue is a client-side javascript view library. We will be using it to create a Single Page App style interface for our project. We will also be using Webpack to compile and minify our front-end assets. Setup instructions for Vue with Webpack will be covered in later parts of this tutorial.

Getting Started

Python

First, you’ll want to ensure that you have Python 3 installed. You can check if you have it installed by opening up your terminal and running the following command:

python3 --version

You’ll want to ensure that you are using at least version 3.5 as the code in this tutorial will not work with older versions of Python.

If you do not already have virtualenv installed, you can install it globally by running the following command:

sudo pip3 install virtualenv

If you are having any trouble installing virtualenv, you can get some more information here and here.

MongoDb

We will need a global install of MongoDb as well. You can go here to find installation instructions for your machine.

NodeJs

We will be using Node to run vue-cli and webpack. Therefore, you will need the Node runtime installed. Most Linux distributions offer a distribution of node in their package managers. You can also download it from the official site linked here.

Setup

Ok, now that we have all of the basic tools we need, we can finally create a directory for our project. Use your terminal to create a new directory in your projects directory with the following command(on Linux):

mkdir movies

Then, move into that directory and create a Python virtual environment:

cd movies/
virtualenv -p python3.5 venv

We then need to activate our virtual environment:

source venv/bin/activate

This will ensure that when we install any packages or call the CPython interpreter, we will be using the packages and interpreter from our virtual environment and not our global environment.

Now we will install our Python dependencies:

pip install hug --upgrade
pip install pymongo
pip install marshmallow

Hug is the web application framework we will be using to create our API. It is quite capable. It’s not only designed for web APIs; it can help you write all sorts of interfaces.

Pymongo, as mentioned above, is the package we will be using to interface with our MongoDb database.

Marshmallow, as mentioned above is the package we will be using to help us enforce data types and serialize to and from JSON.

Code!!!

We’re finally ready to get our hands dirty and write some code! I know it took a while to get here, but I promise it will be worth it. Let’s create a directory for our code to live in:

mkdir app
cd app
touch app.py

Open app.py in a text editor of your choice. We’ll get started with something simple so you can get an idea of how Hug works:

## filename: app.py

import hug  # We need this to define our application


# This decorator is one way that Hug performs HTTP routing. If we leave out the path("/hello"),
# it will default to the name of the function. So, in this particular case, nothing would change.
@hug.get("/hello")
def hello(name: hug.types.text="Anonymous"):
  """
    Returns a response containing a greeting with the user's name.
  """
  return {
    "message": "Hello, {n}!".format(n=name)
  }

We can then run our application by using the following command: (make sure you are in the same directory as app.py)

hug -f app.py

You should see some text on the screen with some information from hug about the application. You can now access your application at http://localhost:8000/. Try opening that address in a web browser or making a request using a CLI tool like curl or httpie. You should receive some JSON back with information about the routes of your API. This is because we haven’t defined a root route yet.

Now try making a request to http://localhost:8000/hello. You should receive the following:

{
  "message": "Hello, Anonymous!"
}

Now try it with your name: http://localhost:8000/hello?name=John. Pretty cool, huh? I hope this illustrates the basic operation of the Hug library.

Outlining our Application

I suppose I should probably tell you what we’ll be building. We will be building a basic movie database! You can think of it like a simple IMDb. I chose this application for this tutorial for a couple of reasons:

  • It’s complex enough that the concepts expressed will have real-world applications.
  • It’s simple enough that It won’t take weeks to build.
  • I’ve been working on a very similar project for my day job.
  • It involves data relationships. Many developers struggle with defining data relationships with MonogDb.

Goal

Let’s define some functions of our application.

  • Users should be able to create accounts.
  • Users should be able to create films. They should also be able to add data about the films they add.
  • Users should be able to add credits to those films.
  • Users should be able to view details about a film.
  • Users should be able to view credits for a film.
  • Users should be able to edit existing films and credits.

Woo! That seems like a lot of work! Luckily, the devil is in the research. Once we know about all of the tools to put this application together, the picture becomes a lot more clear. Luckily, you don’t have to research any tools and libraries for yourself as I’ve already done the hard work for you! I’m such a nice guy.

Data Entities

Ah, data. The core of any worth-while application. Let’s think about how we can organize our data into entities.

Let’s start with the easy one; users. The list items below represent the various pieces of data we will need to store and manipulate. This syntax will be used for the other models as well.

Users

Field Name Data Type Description
username string A unique identifier for the user.
email string The user’s email address so we can contact the user with info about their account.
bio string The user’s biography.
password string The users hashed password. Never store passwords as plain text!!!!

Films

Field Name Data Type Description
title string The title of the film.
synopsis string A brief description of the film.
release_date string An ISO8601 formatted date string representing the date the film was released to the public.

Credits

Field Name Data Type Description
name string The name of the person receiving the credit.
job string What the person did on the film.
department enum Which department the person worked on. ex: Acting, Writing …

That covers the 3 big ones. Later on we will need to think about how these pieces of data fit together(how they are related). We will also be storing urls for user avatars, pictures for credits, and film posters. That type of data isn’t core to the application though, so we can leave it for later.

Part 1 Conclusion

That’s it for part one. I know it doesn’t seem like we’ve accomplished much, but we really have. We’re all ready to start implementing our application now. We have all of the tools and libraries that we will need at this stage of development, we have a good idea of what our application needs to accomplish, and we have a basic outline for our persistent data! Part 2 will likely be coming within the next couple of weeks, so stay tuned!

Comments