Working Code Podcast - Episode 165: Agile Methodology With Brian Sadler
For the most part, software engineers like the concept of Agile methodology; and, they have a sense that agile development practices are the best way of getting work done. But, that doesn't mean we know how to put these agile practices in place (especially at scale). Today, we talk to Brian Sadler (@brian_sadler)—a seasoned software developer and Agile coach—about what Agile is, what parts of it work the best, and where teams often go wrong in their interpretation of best practices.
All that and more on this week's show:
... featuring these beautiful, beautiful people:
- Adam Tuttle → Website, Twitter, LinkedIn
- Carol Weiler → Twitter, LinkedIn
- Tim Cunningham → Twitter, LinkedIn
- Ben Nadel (that's me) → Website, Twitter, LinkedIn
With audio editing and engineering by ZCross Media.
For the full show notes and links, visit the episode page. And, be sure to follow the show and come chat with us on Discord! Our website is workingcode.dev and we're @WorkingCodePod on Twitter and Instagram. New episodes drop weekly on Wednesday.
Reader Comments
Great podcast! I really enjoy the 'triumph & failures' section and I was thinking about your 'authorisation' comments.
Currently, I favour using a JWT, for authorisation/authentication, mainly because I tend to use Angular, for my front end. I figure you are using a fully server side rendered [Coldfusion front & back end ] website for your poetry application, so a JWT, wouldn't really work. In these cases, I just use session validation.
Now here comes the magic. I now pretty much always use FW1, for my Coldfusion based websites. It is a light MVC framework. But, it has some wonderful little features like a 'before' function, in each controller. This is where I do all my session validation stuff. Essentially, this method runs automatically before every request. I have also built a Struct in the request scope that determines what permissions a user needs, to access a certain routes. Combining these two features, I can implement a really clean, efficient auth routine that I can guarantee will work before, a route is executed:
https://framework-one.github.io/documentation/4.3/developing-applications/
Now, I realise that you can't just use FW1, if you have spent years, building a custom application, but actually you can add FW1 subsystems to custom projects, to handle specific functionality.
Anyway, these are my thoughts! 🙂
And it would be great to add a delete function to your comments section.
Unfortunately, I keep forgetting that your comments section doesn't play nicely with mobile Safari.
After just one char, your form auto submits. Hence all my weird one letter comments. 😆
I now write my comments in Apple Notes and then copy & paste, into your textarea.
And I don't even need to press the submit button.
Bargain. 🙂
@Charles,
Yeah, this submitting partial comments things is really frustrating because nothing appears to be actually "breaking". Meaning, I just plugged my phone into the computer and did some remote-debugging in Safari, and there's no errors being thrown. It seems like Hotwire Turbo isn't intercepting the submission properly. It's supposed to be submitting the "preview" request and then swapping-out the HTML for the preview area. But, instead, it's just submitting the form as a normal submission.
Basically, I have this code:
... which is supposed to submit the form via this button:
If there's no JavaScript intercepting the call, then the
formAction
andformTarget
attributes on this button are supposed to override the default behavior of the form. But, they don't appear to be working.This feels like a bug in Safari on iOS. I think I what I need to do is completely replace the approach - instead of leaning on Hotwire Turbo to handle the preview, I need to just revert back to making an explicit API call and using
innerHTML
. Just so frustrating 😨@Charles,
I actually use FW/1 at work. It's a great, light-weight framework indeed. The one thing that I've always wished that it has was a subsystem-level global error handler. As far as I know, all errors have to be handled at the root
Application.cfc
level.What I'm building isn't so different than FW/1 - it's just using
cfinclude
and.cfm
templates instead of CFCs for the controllers. At the top of thecfinclude
that represents a "subsystem", I have a call that looks like this:This is acting like my
before()
call, and is inspecting the cookie and getting the user associated with the current session. Once I have that user, all the calls into my more business-related components pass therequest.user.id
as the first argument (ie, the authenticated user). It's inside those calls that I am then trying to figure out if the given user has permission to perform the requested action.To be fair, even at work, with FW/1, I struggle with the same logic. I never had anything that felt "correct". There's just something missing. Something's in the wrong place.
This Hotwire stuff sounds interesting 👏🏻
So, one last comment about your podcast.
I was just listening to Episode 121, about unit testing.
I'm right with you, about testing.
In fact, I'm thinking about using CoPilot to write my unit tests, because, in theory, they should be ideal candidates, for AI.
CoPilot knows what to test, because theoretically every block of code requires a test. So, not just every method, but every block of code inside that method etc. I really don't think a developer should need to spend time, writing unit tests, when a system can now do the job. The hard part about building an application, is understanding context and how to wire functionality. These kinds of job should be exclusively left to a developer.
Now when Adam gave us his example of building a calculator, I was screaming at my iPhone, which was kind of awkward, as I was in a coffee shop, at the time ;)
But, I remember him saying that one of the tests should emulate a user, pressing the 1 and the 5 button and asserting that 6, should be displayed, in the calculator's input.
Now, I'm thinking this is the wrong thing to test, because you would then need to test an infinite number of button pressing combinations to give a fair representation of this test. Instead, I would just test to see if a press, from 0 through to 9, displays the correct digit, in the input?
And, even this seems, a little pointless. 😆
However, my dislike of testing is more about the fact that humans shouldn't NEED to do this job, when a computer should be able to do this stuff, with relative ease.
When I was working for the Ministry of Justice, UK Government, as an Angular Dev, the managers were insanely strict about testing. We ended up, spending more time, creating unit tests than actually writing code, which is insane, in anyone's book.
Unit testing, in itself, can be a valuable exercise, in certain situations. For instance, I recently did a migration, for a large UK Corporation, called City & Guilds, from Coldfusion 11 to Lucee 5.4. Unfortunately, because it was a legacy project, no unit tests had been written.
Firstly, we thought it might be a good idea to write a compatibility document, highlighting all the differences, in method parameter names/order and tag attribute names etc
Then, we went through features, like the difference between caching, web services, soap, cfhttp, cfquery and many more features.
But, after having picked all the low hanging fruit, we came to a bit of road block.
What we wanted were unit tests that we could run, in Lucee and see where all the errors were being thrown. This would have taken maybe 15 minutes to run and would have hopefully shown us every error and it's location, in the code base! Unfortunately, there were no unit tests to be found, anywhere. 😣
Instead, we had to go through every section and sub section and sub sub section etc, on the screen, to find out where the errors were.
Just the process of using a browser to find every section and learn how to use the UI, was incredibly time consuming.
This approach probably took an extra 2-3 months, to carry out.
So, writing unit tests, for this situation, would have made a vast difference to our own sanity and the budget. But, a migration like this, is somewhat of an edge case, because most modern applications, update their tool chain & code base, incrementally.
So, my final thought on unit testing is that it can be valuable, in certain circumstances, but most of the time, it is vastly overused. 🤷♀️
@Charles,
For me, it's the big wide-sweeping changes, like upgrading from ColdFusion 11 to Lucee 5, where I can see a huge value in testing. Specifically because everyone's fear is 100% right - you have to execute every corner of the app to find edge-cases.
I remember when we switched from ACF to Lucee, there was a huge issue that we didn't find before launch. As you might remember, ACF Arrays were historically pass-by-value (ie, copy on assignment). Lucee, on the other hand, passed Arrays around by reference. In 99 out of 100 cases, this is totally fine and shouldn't cause a problem. But, we had one method in the application that was actually leveraging the fact that Arrays were passed by value (and it was coded specifically to use that behavior). So, when we switched, that method started completely breaking in its assumptions.
The break was really bad and actually caused a security incident.
Now, it's somewhat ironic to even talk about this in the face of testing because I'm not sure testing would have even caught this problem. The issue wasn't that the code worked "incorrectly" for a given user. The issue was that the pass-by-reference made this piece of code unsafe in concurrency. So, it only became a problem when you had multiple requests accessing the code at the same time.
I don't remember the exact details (this was some years ago); but, I believe it had to do with a variable (Array) that was being used as a "template" with default values. In ACF, when the template Array was referenced in the
local
scope of a function, it was copied implicitly, giving each user its own copy. But, in Lucee, suddenly every user was referencing the same Array instance because thelocal
assignment was no longer copying the array, but, instead, was referencing it. 😱😱😱😱All to say, this stuff is complicated. And, that code was pretty bad to begin with. 🤣
OK, I think I fixed the comment submission feature. I am currently writing this on my iPhone. And, it's not auto-submitting the form. I had to strip-out Hotwire on the Preview button (which was hidden from the UI) and manage the preview manually via
fetch()
. Thankfully, the Turbo API has a way to then manually apply the Turbo Stream response HTML to the page viaTurbo.renderStreamMessage(html)
.Post A Comment — ❤️ I'd Love To Hear From You! ❤️
Post a Comment →