DaedTech

Stories about Software

By

How Not to Be Blocked

In a recent post, I talked about how demoralizing it can be to sit around with nothing to do while waiting for someone else to finish a task that you need, fix something that you need, assign you something, etc. I think this is fairly universally known as “being blocked”. It seems nice to have an excuse to do nothing, but I think it makes anyone conscientious a little nervous that someone is going to come along and judge them for malingering, which is rather stressful.

I didn’t really go into details there, but there are many ways to be active, rather than reactive, about being blocked (I think most would have said “proactive”, but I think I kind of hate that word for seeming bombastically redundant — but don’t mind me if you use it because I’m weirdly picky and fussy about words). Taking action not to be blocked has a variety of benefits: alleviates boredom, helps your company, boosts your reputation, opens up potential additional opportunities, etc. The way I see it, being blocked is something that you can almost always manage and opt out of. When I worked in retail many years ago, there was an adage of “if there’s time to lean, there’s time to clean.” I would say the equivalent in the world of software development is “if you’re blocked, you aren’t trying hard enough.”

Things to do when you’re blocked:

  1. Start a wiki or sharepoint site. There’s no company or domain out there that can’t use more documentation and information for onboarding and general reference. And these collaboration mechanisms are perfect since they’re designed to be imperfect at first and refined over the course of time.
  2. Get a subscription to pluralsight and polish your skills. Whether for the sake of the company or the sake of your own career, there’s no engineer that couldn’t use a few new useful tidbits.
  3. Get ahold of a backlog of defects or nettlesome issues for one of the pieces of software your group writes/maintains, create a playpen, and dive in. You’ll learn more about the code and you might even solve one or more issues that have plagued the team for a while.
  4. Identify a pain point for your fellow developers and do something about it. For instance, if merges constantly mess up a file in your code base, write a utility they can use to validate that file. It’s a lot more useful to the company than reading reddit or slashdot and it’ll boost your cred with your fellow developers as well (that is, help you pass “the second test“).
  5. Ask the people around you if they need a hand with anything. There are often people willing to offload a task or two, especially if it’s grunt work or if they’re stressed and you’re keeping yourself busy and earning some pennies in heaven doing this.
  6. Offer to go through an existing code base, adding or creating documentation for it. This has the useful dual purpose of improving documentation and helping you learn the code. When you know something well enough to explain it to others, you know it pretty well.
  7. Abstract, abstract, abstract. If it’s a development task, make an assumption about the info you’re waiting on, and code the rest of the system as if this assumption were true. Then code the system in such a way that changing your assumption is simple. For instance, don’t say “I can’t work until we decide what RDBMS to use — just write some kind of CRUD interface that your system uses with no implementation and go on your merry way.

I think that’s more than enough ammunition to ensure that you’ll always have some non-loafing task to do at the office. If you can find a situation where none of those things is an option, then my hat’s off to you or, perhaps more appropriately, my sympathy goes out to you because you probably need to find a new job. But maybe you can take steps to avoid being blocked in the first place. This list is a bit more abstract and a much less foolproof, but I’d suggest the following practices to avoid being blocked in general.

  1. Seek out situations where you have multiple assignments at once. This requires managing expectations and good organization and prioritization skills, but the end result is that you’ll have approved, productive work to fall back on even when waiting for answers.
  2. Cultivate a healthy knowledge of the problem domain you’re working on. In my experience, a lot of blocking results from needing someone to tell you what “Taking the EBE out of the PHG with the ERBD” means. The more domain knowledge you have, the more chance you have of deciphering cryptic acronyms and jargon code that prevents you from figuring out what to do next.
  3. Seek out areas in which you’re the main decision maker, however small they may be. I understand that you cant’t exactly promote yourself to VP of Engineering, but if you seek out being in charge of something, even if it’s just a small, low priority tool or something ancillary, you
    are unlikely to be truly blocked.
  4. Become resident expert in some technology, product, facet of the business or tool that matters. Generally people who are expects (e.g. the database expert or the source control expert) are in high demand and can fill any lulls with meetings and cooperative sessions with those seeking their expertise.

If you have other ways to avoid being blocked, I’d be interested to hear about them in the comments. I think avoiding blockages is critical not only for preserving your reputation, but preserving your sense of purpose and, on a long enough timeline, your engagement and work ethic. Don’t fall into the trap of checking out due to lack of stuff to do. Make sure you have stuff to do. And, if all else fails, move on. Or, to adapt an aphorism I’ve heard from enough places so as to be unsure of the original source, “change your work circumstances or… change your work circumstances.”

By

ASP Webforms Validation 101

Today I’m going to delve into a topic I don’t know a ton about in the hopes that someone who knows less than me will stumble onto it and find it helpful. As I’ve alluded to here and there, I’ve spent the last couple of months doing ASP Webforms development, which is something I’d never done before. I’ve picked up a handful of tips and tricks along the way. Today I’m going to walk through the basics of validation.

Start out by creating a new ASP.NET Webforms project:

This gives you an incredibly simple Webforms project that we can use for example purposes. If you open up the login form, you’ll find a boilerplate login form laid out in markup. Let’s take a look at the User Name controls:

  • User name
  • What we’ve got here is the most basic form control validator, the required field validator. The “ControlToValidate” attribute tells us that it’s going to validate the “UserName” text box and the “ErrorMessage” attribute contains what will be displayed if the validation fails (i.e. there is nothing in the field when you submit the form):

    Pretty standard stuff. Let’s switch things up a little, though. Let’s add another label after the text box with something goofy like “is logging in.” This is something I bumped into early on as a layout issue and had to poke and google around for. Here’s the new look for the markup:

  • User name is logging in.
  • And here’s what it looks like:

    But that’s no good. We want this on the same line as the text box itself or it looks even goofier. Well, counterintuitive as it seemed to me, the validator field defaults to taking up the space that it would occupy if it were always visible. You can alter this behavior, however, by adding the attribute Display=”Dynamic” to the validator tag. Once you do this, the new label will appear on the same line–unless you mess up. Then the validator will resume taking up space, bumping the new label to the next line. Okay, okay, I’m no UX guru, but the important thing here is that you can set the space occupation behavior of your validators.

    The next lesson I learned was that I could use validators for comparing values as well as doing typechecks. This tripped me up a bit too because I would have assumed that there was some kind of TypeCheckValidator, but this isn’t the case. Instead, you have to use CompareValidator. Let’s say that we want users to have to log in with a decimal representing a valid currency. (“Why,” you ask? Well, because we’re insane 🙂 .) This is what it would look like:

  • User name is logging in.
  • The new validator shares some commonality with the existing one, but take special note of the “Operator” and “Type” attributes. Both of these fields are necessary. For anyone who has read my various rants about abstractions, would you care to guess why I found this completely unintuitive? Well, I don’t know about you, but I personally don’t tend to think of “DataTypeCheck” as an “Operator” (perhaps an “operation,” but even that seems like a stretch). I would have expected either a DataType validator or else the Compare validator simply to need the type specified, at which time it would do a type check. But, I digress.

    The next sticking point that I encountered was that I had a particular form where I wanted to validate something that wasn’t part of a text box. I thought I was dead in the water and would have to do something sort of kludgy, but CustomValidator was exactly what I needed. Let’s say that I wanted to verify that the weird label I’d created does not, in fact, contain the word “is.” (This isn’t necessarily as silly as it sounds if there’s code that alters this label dynamically based on other inputs.) If I point any validator at this control as the “ControlToValidate”, I’ll get an exception saying that it cannot be validated. But I can omit that property and specify an event handler.

    Add the custom validator to your markup and you get this:

  • User name is logging in.
  • And add the following to your code behind:

    public void PointlessLabelValidator_ServerValidate(object sender, ServerValidateEventArgs e)
    {
        var labelText =((Label)LoginControl.FindControl("PointlessVerb")).Text;
        e.IsValid = !labelText.Contains("is");
    }
    

    Now launch the web app again and type a number for the user name and something for the password and observe the new error message. It’s important to note here that you need to satisfy the other validation constraints because the custom validator operates a little differently. The validators we’ve added up until now work their magic by sending validation java script over the wire to the client and so validation is client-side and immediate. Here, we’re performing a server-side validation. This server-side custom validation will be short-circuited by client-side failures, which is why you need to fix those before seeing the new one.

    And that’s my brief primer on validators. This is neither exhaustive nor the equivalent of a nice book written by a Webforms guru, but hopefully if you’re here it’s helped you figure out a few basics of Webforms validation.

    By

    Old Programmer’s Guide to Practical Maths

    I’m writing this post to introduce another series of posts I intend to embark upon, to coexist alongside my “abstractions,” “design patterns,” and “home automation” posts. I’m going to post these under the category “Practical Math” and think of the series as being called “Practical Math for Programmers,” the title of this post notwithstanding. (Speaking of which, bonus Renaissance-Man points to the first commenter who knows what inspired the title.)

    Does Math Matter?

    This is a discussion that I’ve heard a lot over the years as a programmer, and it seems to be a slightly more muted and cordial debate than the typically contentious “computer science degree vs certifications” or “schooling versus self-taught” ones. Generally the accepted answer is the “architect answer” of “it depends.” I’ll see/hear consensuses such as, “well, you need it if you’re going to be doing really low level stuff or processing lots of data or designing compilers or something, but if you’re just writing basic line of business apps or if you’re more of a designer then you don’t need math.” I often like the architect answer because trending toward nuance and avoiding absolutes gives you the most chance of recovering from bad assumptions, but I’m going to go out on a limb here with more of a hard-line stance. I think that programmers do need and use math and that it doesn’t “depend” at all. It’s just that some are more trained in and aware of their usage of it while others do it by intuition, rote, or dependence on others.

    One thing that I think clouds the issue is what is meant by “math.” Many think back to derivatives or perhaps back further to trigonometry and algebra and realize that they don’t frequently hit the math libraries for things like cosine or solve for x. Sure, there are some basic arithmetic operations when laying out a page–addition, subtraction, etc., but that’s it. There’s a broad tendency to dismiss the basic arithmetic as too trivial for discussion and declare math unnecessary in these cases.

    But I think that this analysis tends to overlook two math concerns: missed opportunities to leverage math and lack of understanding that it’s even being used. For the first one, consider a scenario of laying out a form with simple arithmetic. Say there are three buttons that need to be evenly spaced on a form, and the form should have a fixed width, but you have some control over that. The visual, “non-math” way to do this might be to assign the buttons random horizontal locations and then move them around by trial and error. Time could be saved, however, with a simple algebraic solution of determining a ratio of padding to button, determining a form width, and solving for x–no trial and error and exactly right the first time.

    The second concern is a bit more subtle. Perhaps each of the aforementioned buttons have handlers and those handlers have some logic. If button 2 is clicked after button 1, and button 3 is red or else button 2 is blue, disable button 1. Is there any math there, or just a series of weird procedures? The answer is “both,” but you’re probably not thinking of or looking for the math. You’re intuitively constructing logic chains in your head and trying to figure out where the nested parentheses are going to go in your if statement. If you’re intuitively constructing scenarios and you think you’re not doing any math, it’s because you’ve never been exposed to truth tables or Boolean algebra.

    It Definitely Matters

    Boolean logic lies at the core of most things that any programmer does, and it isn’t alone. Arithmetic is obviously indispensable, if reasonably taken for granted, but at the core or arithmetic lies the cousin of Boolean algebra, which is algebra over real numbers. Pulling back from the more “fluid” concerns about real numbers with which we’re used to dealing, there is also a whole world of discrete/finite math that involves distinct values and forms the basis for concepts like sets, graphs, and basic data structures which are in turn assembled into algorithms and design patterns. From that emerges everything from the exotic, like cryptography, to the mundane, such as preconditions and functions. If you’re a programmer and haven’t had exposure to these things, you’re living in The Matrix, blissfully unaware that you could take a red pill and start to see everything you’re doing as a weird, dripping series of green symbols and digits on black background.

    Because I think that math matters a lot and because it’s fairly heavily in my background, I’m going to embark upon this series of posts. I’d like to cover things such as DeMorgan’s Laws/Boolean Inference, O-notation, formal methods, combinatorics, probability/game theory, etc. But if you find your eyes glazing over just reading that list, don’t worry–it won’t be a bumpy ride. And I’ll be in it with you, since my days of heavy exposure to theoretical math are, along with college and grad school, surprisingly far away in my rearview mirror. I’ll have some rust to shake off myself. These are going to be very elementary explanations of these concepts, along with practical concerns of why you as a programmer should care. I’ll also provide links to more information and formal reading along with perhaps examples of where you’re already using this and maybe not even realizing it. I’m going to keep these posts mainly language agnostic, and I might switch it up among C#, Java, and C++, depending on what I’m covering.

    Stay tuned if this kind of thing interests you.

    By

    The Myth of Quick Copy-And-Paste Programming

    Quick and Dirty?

    “We’re really busy right now–just copy that customer form and do a few find and replaces. I know it’s not a great approach, but we don’t have time to build the new form from scratch.”

    Ever heard that one? Ever said it? Once, twice, dozens, or hundreds of times?

    This has the conversational ring of, “I know I shouldn’t eat that brownie, but it’s okay. I’m planning to start exercising one of these days.” The subtext of the message is a willingness to settle–to trade self esteem for immediate gratification with the disclaimer “the outcome just isn’t important enough to me to do the hard thing.”

    If that sounds harsh to you when put in the context of programming instead of diet and exercise, there’s a reason: you’re used to fooling yourself into believing that copy-and-paste programming sacrifices good design to save time. But the reality is that the “time savings” is a voluntary self-delusion and that it’s really trading good design for being able to “program” mindlessly for a few minutes or hours. Considered in this light, it’s actually pretty similar to gorging yourself on chocolate while thinking that you’ll exercise later when you can afford that gym membership and whatnot: “I’ll space out and fantasize about my upcoming vacation now while I’m programming and clean up the mess when I come back, refreshed.”

    Hey, Wait a Minute

    I know what you’re thinking. You’re probably indignant right now because you’re thinking of a time that you copied a 50,000 line file and you changed only two things in it.

    Re-typing all 50,000 lines would have taken days, and you got the work done in minutes. The same number of minutes, in fact, that you’d have spent parameterizing those two differences and updating clients to call the new method, thus achieving good design and efficiency. Okay, so bad example.

    Wait, Now I’ve Got It

    Now, you’re thinking about the time that you copied that 50,000 line file and there were about 300 differences–no way you could easily have parameterized all of that. Only a copy, paste, and a bunch of find and replace could do the trick there.

    After that, you were up and running in about an hour. And everything worked.

    Oh, except for that one place where the text was a little different. You missed that one, but you found it after ten minutes of debugging.

    Oh, and except for five more of those at ten or fifteen minutes a pop.

    Oh, and then there was that twenty minutes you spent after the architect pointed out that a bunch of methods needed to be renamed because they made no sense named what they were in the new class. Then you were truly done.

    Except, oh, crap, runtime binding was failing with that other module since you changed those method names to please the stupid architect. That was a doozy because no one noticed it until QA a week later, and then you spent a whole day debugging it and another day fixing it.

    Oh, and then there was a crazy deadlock issue writing to the log file that some beta customer found three months later. As it turns out, you completely forgot that if the new and old code file methods executed in just the right interleaving, wackiness might ensue. Ugh, that took a week to reproduce and then another two weeks to figure out.

    Okay, okay, so maybe that was a bad example of the copy-and-paste time savings.

    Okay, Those Don’t Count

    But you’re still mad at me. Maybe those weren’t the best examples, but all the other times you do it are good examples.

    You’re getting things done and cranking out code. You’re doing things that get you 80% of the way there and making it so that you only have to do 20% of the work, rather than doing all 100% from scratch. Every time you copy and paste, you save 80% of the manpower (minus, of course, the time spent changing the parts of the 80% that turned out not to be part of the 80% after all).

    The important point is that as long as you discount all of the things you miss while copying and pasting and all of the defects you introduce while doing it and all of the crushing technical debt you accrue while doing it and all of the downstream time fixing errors in several places, you’re saving a lot of time. I mean, it’s the same as how that brownie you were eating is actually pretty low in calories if you don’t count the flour, sugar, chocolate, butter, nuts, and oil.

    Come to think of it, you’re practically losing weight by eating it.

    We Love What We Have

    Hmm…apparently, it’s easy to view an activity as a net positive when you make it a point to ignore any negatives. And it’s also understandable.

    My flippant tone here is more for effect than it is meant to be a scathing indictment of people for cutting corners. There’s a bit of human psychology known as the Endowment Effect that explains a lot of this tendency. We have a cognitive bias to favor what we already have over what’s new, hypothetical, or in the possession of others.

    Humans are loss averse (we feel the pain of a loss of an item more than we experience pleasure at acquiring the item, on average), and this leads to a situation in which we place higher economic value on things that we have than things that we don’t have. You may buy a tchotchke on vacation from a vendor for $10 and wouldn’t have paid a dollar more, yet when someone comes along and offers you $12 or $20 or even $30 for it, you suddenly get possessive and don’t want to part with it. This is the Endowment Effect in action.

    We Love Our Copy Paste Code

    What does this have to do with copying and pasting code? Well, if you substitute time/effort as your currency, there will be an innate cognitive bias toward adapting work that you’ve already done as opposed to creating some theoretical new implementation. In other words, you’re going to say, “This thing I already have is a source of more efficiency than whatever else someone might do.”

    This means that, assuming each would take equal time and that time is the primary motivator, you’re going to favor doing something with what you already have over implementing something new from scratch (in spite of how much we all love greenfield coding). Unfortunately, it’s both easy and common to conflate the Endowment Effect’s cognitive bias toward reuse with the sloppy practice of copy and paste.

    At the point of having decided to adapt existing code to the new situation, things can break one of two ways. You can achieve this reuse by abstracting and factoring common logic, or you can achieve it by copy and paste.

    Once you’ve already decided on reuse versus blaze a new trail, the efficiency-as-currency version of the Endowment Effect has already played out in your mind–you’ve already, for better or for worse, opted to re-appropriate existing work. Now you’re just deciding between doing the favorable-but-hard thing or the sloppy-and-easy thing. This is why I said it’s more like opting to stuff your face with brownies for promises of later exercise than it is to save time at the expense of good design.

    Copy Paste Programming as Empty Calories

    Think about it. Copy and paste is satisfying the way those empty calories are satisfying. Doing busy-work looks a lot like doing mentally taxing work and is often valued similarly in suboptimally incentivized environments.

    So, to copy and paste or not to copy and paste is often a matter of, “Do I want to listen to talk radio and space out while getting work done, or do I want to concentrate and bang my head against hard problems?” And if you do a real, honest self-evaluation, I’m pretty sure you’ll come to the same conclusion.

    Copying and pasting is the reality television of programming–completely devoid of meaningful substance in favor of predictable, mindless repetition.

    Quick and Dirty is Just Dirty

    In the end, you make two decisions when you go the copy-and-paste route. You decide to adapt what you’ve got rather than invent something new, and that’s where the substance of the time/planning/efficiency decision takes place. And once you’ve made the (perfectly fine) decision to use what you’ve got, the next decision is whether to work (factor into a common location) or tune out and malinger (copy and paste).

    And in the end, they’re going to be a wash for time. The up front time saved by not thinking through the design is going to be washed out by the time wasted on the defects that coding without thinking introduces, and you’re going to be left with extra technical debt even after the wash for a net time negative.

    So, in the context of “quick and dirty,” the decision of whether new or reused is more efficient (“quick”) is in reality separated from and orthogonal to the decision of factor versus copy and paste (“dirty”). Next time someone tells you they’re going with the “quick and dirty” solution of copy and paste, tell them, “You’re not opting for quick and dirty–you’re just quickly opting for dirty.”

    By the way, if you liked this post and you're new here, check out this page as a good place to start for more content that you might enjoy.

    By

    FluentSqlGenerator

    A while back, I made a post about using string.Join() to construct SQL where clauses from collections of individual clauses. In that post, I alluded to playing with a “more sophisticated” where clause builder. I did just that here and there and decided to post the results to github. You can find at here if you want to check it out.

    My implementation makes use of the Composite design pattern and the idea of well formed formula semantics in formal systems such as propositional and first order logic. The latter probably sounds a little stuffy and exposes my inner math geek, but that’s just a rigorous way of expressing the concept of building a statement from literals and basic operations on those literals. To pull it back yet another level of stuffiness, consider simple arithmetic, in which all of the following are valid expressions: “6”, “12 + 6”, “12 + (9 – 3)”. The first expression is an atomic literal and the second expression a binary operation. The third expression is interesting in that it shows that functions can have arguments that are literals or other expressions (if this still seems strange, think of these examples as “6”, “Add(12, 6)” and “Add(12, Subtract(9, 3))”.

    Think of how this applies to the propositional semantics that make up SQL query where clauses. I can have “Column1 = 12” or I can have “Column1 = 12 AND Column2 = 13” or I can have “Column1 = 12 AND (Column2 = 13 OR Column3 = 4)”. When I want to model this concept in an object oriented sense, I need to represent the operators “AND” and “OR” as objects with two properties: left expression and right expression. I also need it to be possible that either of these properties is a “literal” of the form “col = val” or that it could be another expression as with the last example. Composite is thus a natural fit when you consider that these clauses are really expression trees, in a very real sense. So there is a “Component” base that’s abstract and then “Clause” and “Operation” objects that inherit from them and are fungible when constructing expressions.

    This was the core of the implementation, but I also dressed it up a bit with some extension methods to support a discoverable, fluent interface, but optionally (I’m still very leery of this construct, but this seems like an appropriate and judicious use). Another nice feature, in my opinion is that it supports generic parameters so you don’t have massive overloads — you can set your columns equal to objects, strings, decimals, ints, etc. It makes heavy use of ToString() with these generic parameters, so use any type you please so long as what you want out of it is well represented by ToString().

    A sample API is as follows:

    var clause = Column.Named("Column1").IsEqualTo(123);
    Console.WriteLine(clause);
    
    clause = Column.Named("Column1").IsEqualTo(123).And(Column.Named("Column2").IsEqualTo("123456"));
    Console.WriteLine(clause);
    
    clause = Column.Named("Column1").IsOneOf(1, 2, 3).Or(Column.Named("Column2").IsGreaterThan(12));
    Console.WriteLine(clause);
    
    clause = Are.AnyOfTheseTrue(Column.Named("Column1").IsEqualTo(832), Column.Named("Column2").IsLessThan(25.30));
    Console.WriteLine(clause);
    
    clause = Are.AreAllOfTheseTrue(Column.Named("Column1").IsEqualTo(832), Column.Named("Column2").IsLessThan(25.30), Column.Named("Column3").IsOneOf("Current", "Valid"));
    Console.WriteLine(clause);
    
    Console.ReadLine();
    

    Currently supported SQL operations include various comparison (equal, not equal, greater, less, etc) as well as “like” and “in()”. Expression operators “AND”, “OR” and “NOT” are supported. The utility is well covered by unit tests and a handful of integration tests too if you want to poke around but preserve functionality.

    Feel free to download, use, fork, enhance, make fun of, etc, whatever. I’m not pretending this is a problem never before solved nor that this is the most elegant solution imaginable, but it was fun to write, code-kata style, and if someone can get some use out of it, great. If I wind up making significant modifications to it or extending it, I’ll post updates here as well as checking changes into github.