Software Engineer
100 hours of Django
October 19, 2020

The Reason

A pet project that I've been kicking around for a while now is I had a vision for a job board where posted salaries were required. The lack of transparency is quite frustrating, as I imagine some of you would agree. There are reasons for it, but I feel like they are bad reasons, especially in the current employee-driven market. No one wants to interview for a job only to find that after four or five interviews, this new job pays 30% less than your previous one.

So I started work on Solists. I wanted a fully detailed, honest, held-accountable system. No more hiding behind nebulous salary clouds or "competive wages". No more vague job descriptions, or bad information. THE MVP for the site was for users to be able to make accounts, either to post jobs for a small fee, or to set up a developer / designer and make a small portfolio. I was sick of postings with inaccurate or bad information, so the entire point of the matter was that before ANY jobs got posted, I did a full review on them. This was not about the money so much, as a healthier, smarter job-ecosystem for software professionals and those who were trying to hire them. And since I like to tinker and learn, I was also looking for an excuse to dust off a backend framework and get into the nitty-gritty of it.

Also, I wanted something that I didn't have to roll my own authentication/encryption layer, and Django had been my very first dip into software development for a brief time before trending towards frontend / JAMstack work, I needed something reliable. Django was a mature system, had an admin dashboard that I could dig closer and review before allowing changes, and was accessible and known to be sturdy and maintainable. While after a few years of working, I have learned that there is rarely the best tool for every job, Django was the right tool for this job.

Enter Django

Being a mostly frontend JS - React - Gatsby guy, I hadn't had the chance to use any frameworks with the MVC model, but after a littler finagling, I found that I was really enjoying myself, and the docs were just lovely.

The process is fairly simple, and while this isn't going to be a super-technical post, I do want to describe the general ecosystem so I can talk about some of the specifics. The Django tutorial is amazing, and there are also the books by William Vincent that were just lovely.

First, The user installs Django however they wish (I use pip and pipenv, but other alternatives exist.) Then, run django-admin startproject config (You can also replace config with any other name you'd like.)

This creates the main folder for Django apps. It consists of an,,,, and We only really care about the and at this point.

The process is linear from there, and follows almost the same setup every time. The user will create a new app with python startapp appname. That app gets added to, and the path in Inside the app itself, the user sets up the database models, the urls, the views, and then hooks it up to a template. The same five or so steps, every time, for every app.

The user then splits up different functionality in different apps. In mine, I have one for basic pages, users, leads, and orders.

Version 1 and 2, Django and DRF

The very first iteration of the site was in pure Django. Then, frustrated with my initial works of the template pages, and full-time as a frontend software engineer for a startup, I got to thinking. "I know how to do the frontend", I thought. "I'll just split it up, use React on the frontend, and Django Rest Framework on the backend. Imagine all the time I'd save!"

And so I split up the project, and it worked quite well at start. I can do a frontend with my eyes closed and tied up in a room blindfolded, and there was just one problem.

It wasn't fun.

There are serious reasons to split a project up, but if we follow the YAGNI principal (Ya ain't gonna need it), it was a waste. Separating a backend-heavy project into a frontend and a backend creates a ton of extra work, I found myself duplicating work, and creating serializers for the data to go back and forth, and it was just too much. At it's core, all it needed was Users, Pages, Leads, Views, and Ordering with Stripe. The real kicker was when I found a bug with one of the Django pip apps I'd been using, django-multiselectfield. Having been mapping my data on the frontend, a tried and true method, I suddenly found that when I only had one item selected for skills, rate, experience (all fields I'd set up to have multiple options, and not limited to just just one at a time), my map would fail, loudly, taking down both my development environment and my online """production""" site. I didn't get it, and it took me four or five hours to finally track down the root of the problem.

It turns out that the multiselect field when there was more than one item was a tuple, which is basically in python's array if you are only familiar with JS. Arrays are mappable, and easy to work with, so shouldn't have been a problem. Except, when the multiselect field only had a single argument saved it sent the data as a string. Now strings, they can't be mapped over. There's only one. That might be weird with how you can do some freaky stuff in JavaScript, but it just doesn't work. Perhaps if I'd been using typescript, I would have caught that error in a matter of minutes, but Typescript comes with its own baggage. Don't get me wrong, it's great for larger projects, but for a smaller project...

Faced with the lack of enjoyment in my side-project, errors in data communications between my frontend and my backend, and using DRF in general, I once again migrated my site back to being Django-only.

Django, part 3

And it was lovely. Since it's initial release was 15 years ago, it makes it one of the most mature frameworks on the web. Every time I hit a problem, somebody had already solved it. Stack Overflow was full of tips and suggestions, and the API itself was flush with shortcuts to make life easier. After spending so much time in younger frameworks, and especially in using and learning some of the new frameworks for Rust, it was just a pleasure. If you haven't gotten a chance, just check out their docs. I think the only docs I've enjoyed even close as much have been the Rust book, but even then, that's not quite the same thing.

After putting some effort into learning WHY Django does things the MVC way, and not just slapping code around, things really started to click. Forms were easy to use, the ecosystem was great, and that multiselect field I had so much trouble with before? Worked just fine being used the way it was supposed to be. Who would have guessed?

Also, another thing. Testing. After five thousand + hours learning at this point, improving, and working as a programmer, I have to say, having the opportunity to do some TDD was the best thing of all. Writing tests to see if the project worked every time I changed something... Now that is just magical. I don't think I could describe it to someone who has never had to hunt down an elusive bug all day long on the frontend, only to find out it was because another developer had changed something days or weeks before and it slipped by without a code review. But the ability to simply type "python test" and see if it all still worked as intended... indescribable.

Ending note is almost complete, and I hope to have it up and running in my spare time in the next week or two, while I continue to interview and prep for grad school on the side. But it's my hope that it will evolve into making the job hunt just a little less painful for those who come after me. Some advanced search, finishing up my unit tests, making sure the payment system works, and maybe add some spots for users to add pictures of their finished projects... we'll see where it ends up going. And at this time, I've already gotten my first buyer for 15 dollars for a posting, so the dream of passive income is alive and well. We live in crazy times, but I'd hate to miss how the ecosystem out there is changing.

You can see some of the Solists source code here. I might end up making it a closed-source app once I finish it up, only to preserve all the hours I spent building it, and to prevent it's modest income stream, but until then, it's available under the GNU GPLv3 license. Poke, tinker, and fork as you please. And if you have anything to add, reach out, I'd be happy to talk with you about whatever it was that caught your attention.