How AI Revolutionized Accessibility for an Educational Platform
I wrote an article on the Zaengle blog discussing how we integrated AI into an application that resulted in the automation of a previously time-consuming process. This wouldn't have been possible without recent advances in AI.
Building Applications That Last
This article collects some of the most important takeaways I've learned after building web applications.
At Zaengle we have built a number of web-based software applications over the past 12 years. Some have been transient, only serving a specific purpose for a window of time, while others have persisted for years on end. We've learned a number of key lessons while building and maintaining these long-term applications and we wanted to share them with you.
Ionic 5 + VueJS + Laravel + JWT

Recently I've been dabbling in building an iOS application for JobStruct, a business management tool for concrete contractors. Since I'm familiar with Vue we decided to use Ionic framework which allows an app to be written in javascript and then run as an application on ios and Android using web views. The two-part article series from Naveen Bommidi regarding authorization with JWT has been a good starting point.
Getting started in Docker
Docker is still a mind-bender for me. Fortunately kind people write detailed articles like this!
Docker for local web development, introduction: why should you care? →
Abstractions and Vacations
Abstraction can be hard to define, but I believe it is a very important skill for developers to hone. I wrote an article detailing my experience with abstraction on the Zaengle blog and here are a few of the high points:
Abstraction is a kind of organization accomplished by delegating responsibilities and information so that each segment isn’t overwhelmed or doing more than its fair share.
Another benefit of abstraction is the freedom it gives to change the internals of a section of code without the fear of breaking larger application logic. If feature A is given input and returns specific output, does it really matter what happens while the logic is inside feature A? That gives me the freedom to design and adjust over time.
Abstraction is a dangerous tool if wielded improperly. A bad abstraction can keep you hopping back and forth in a codebase, scratching your head saying, “Where does this thing happen?
Handling Complex Data Flows
In this post, written for the Zaengle blog, I explore some strategies for navigating multi-step flows. Separating the data from the logic helps make the process more manageable.
"At its core, programming is nothing more than stacking little blocks of logic on each other, building up a structure comprised of detailed organization, intentional design, and functional beauty. Unless those goals are held front and center it is only a matter of time before the system devolves into a convoluted mess of overlapping, overstepping, messy code."
The X-Factor: Or, How To Debug
Have you ever been around a person, or maybe you are that individual, who has the innate ability to figure out what’s wrong with _____? Merely glancing at the computer that is behaving strangely causes the problem to disappear, touching the printer results in printed pages, or opening the hood of the car stops the squealing?
It’s a strange phenomenon, but certain people possess the ability to diagnose a situation, survey the playing field, and effectively implement a solution. I’m sure you’ve seen it happen before.
Truth be told, I don’t believe these people have any special magic. It is far more likely they’ve spent time honing their ability to observe what’s going on, consider possible courses of action, and choose the one that has the best probability of fixing the problem.
This is called troubleshooting.
How We Keep Code Clean at Zaengle
Check this out to see how the team at Zaengle keeps code clean:
Let's be honest, we all like systematic, uniform code. However, maintaining a respectable level of cleanliness across multiple developers' systems can be a challenge. Thankfully there are a few tools to help unify our editors so that our code styling gets along!
Programming for your Future Self
If you are anything like me, you may find yourself hacking on a variety of different applications during a given week. Occasionally I get the luxury of working on a single app, which gives my brain the freedom to immerse itself into the details of the program. However, inevitably at some point I have to set the project aside and fire up a different one… perhaps one that was written months, or even years ago.
Several thoughts have repeatedly surfaced as I re-familiarize myself with an old project. Instead of having to collect them each time, I thought I’d write them down here, to serve as a reminder.
Sorting Parent Eloquent Models by a Child Relationship
Recently I had a situation in a Laravel app where I needed to sort a collection of parent models by a particular value in aBelongsTo()relationship field.
It’s fairly simple to sort the opposite direction, meaning, to sort all the related models that belong to a parent model.
Simplifying Conditional Expressions
As I’ve been reading through Refactoring by Martin Fowler, I’ve found it helpful to rewrite some of the examples from the book in PHP in order to cement the concepts into my mind. While Martin’s examples are primarily in Java, I’ve found an overwhelming majority of the concepts apply to PHP, which is where I spend most of my programming time.
In today’s article, I will attempt to rework the Simplifying Conditional Expressions (pp. 237-270) section into a handful of PHP-based examples.
Diving Into a Laravel Audit
Recently the Zaengle team was asked to look over an existing Laravel application and give a review of the overall state of the code. We were to act as an independent third party, between a new studio who had inherited the codebase, and the client, who was anticipating launching the product. The studio had some concerns about the quality of the code and wanted an independent review prior to picking up development on the project. Here are a few thoughts on the process I followed and several takeaways I had from the experience!
Testing 101: Escape Testing Paralysis!
Learning to write good tests is critical to being a programmer. We write tests to make sure the work is solid and doing what it's supposed to, while exerting as little effort as possible (we're not lazy; we're effective...). When I understood that, I determined that I was going to get great at testing. So naturally I started internet research: "Dear Google, show me 'best code testing practices.'"
I quickly gathered that there are a multitude of testing solutions with numerous opinions on each one. In the same way that children can choose blue LEGO bricks, red ones, or two green ones and then argue loudly about which choice is superior, I heard terms like unit testing, functional testing, integration testing, acceptance testing, etc., and all the debates on what should and shouldn’t be tested in our applications.
I soon found myself in testing-paralysis. My overloaded brain said I had to thoroughly understand each of these paradigms before I could begin implementing any kind of testing on my apps. (Which color LEGO is best?) I didn’t feel confident enough to implement any test, for fear of choosing the wrong test, so I resorted to saying, “Let’s just build the app, and I’ll circle back and test it later.”
Little did I know that even though I thought avoiding the tests was making my life easier, I was actually digging myself into a hole.