Half-Elf on Tech

Thoughts From a Professional Lesbian

Category: How It Works

  • Backtrack to Clean Code

    Backtrack to Clean Code

    I was watching The Bletchley Circle, about four women who were part of the code breakers in World War II, and how they stumbled upon a serial killer because only they could see the patterns. In the third episode of the first season, the main character is trying to explain why understanding the killer, Crowley, from before he started killing, and she says the following:

    At Bletchley, when we came across corrupted data, we had to backtrack till we hit clean code. That’s how you find an error in the pattern. All Crowley’s giving us is corrupted data.We need to backtrack to before he was killing. We need to start from there. That’s how we’ll find him.

    I’d never thought of it in those words, but that’s exactly right.

    When we debug code, when we find errors, we always backtrack to clean code. Most of us aren’t trying to find psychopaths and serial killers, of course. What we’re trying to do is find the patterns and understand what went wrong. And many times, we’re trying to find patterns when the telling of the breaking doesn’t lend itself to any patterns.

    Think about how you describe a situation, how you explain what’s broken. You start with your part. “I was trying to do X.” Then you explain what you expected to happen. “Normally that makes the color blue.” Next you say what did happen. “Instead, it made the color red.”

    That’s all well and good, except there’s a great deal missing. Some of it will be pertinent and some won’t. Some will be overkill and useless signal to noise, and some minutiae will be just what is needed to solve a problem. The difficulty is that you may not know what happened that is important. If all you know is ‘I upgraded WordPress’ for example, then you may not be aware of all the changes that went into the WP_Http API. You may not know about the new Multisite functions.

    If you’re not a developer, reading the field guide for WordPress 4.6 RC1, and all the linked posts, and did a compare of 4.5.3 to 4.6-RC1, then maybe you’d be surprised when your plugin breaks. And while you thought well of yourself for testing on the release candidate, you’re stunned at how much changed, and not sure what on earth happened.

    So you backtrack. You know that the magic sauce is in the requests sent to the server. And you know you’re using wp_remote_request() to do it. So you look at anything related to that. What does it call? Did that change? You step back and back until you find as much as you can, and when you’ve determined it’s ‘something,’ you reach out for help.

    In WordPress, this is why we tell people to switch to default themes or disable plugins. We’re asking people to backtrack to code we know is clean. We can’t read minds and know the little things. So we ask people to backtrack in the most obvious ways. “Does it happen with all the other plugins off?”

    Backtracking to clean code.

  • Keep A Name In Mind

    Keep A Name In Mind

    When you’re making your own project for small things, it’s not a huge deal when you try to think up a name. As soon as you realize your project is going to be shared with the world, however, the game changes.

    Project Names

    A project can be as massive as a new release of an operating system (Longhorn anyone?) or as small as a new plugin for WordPress. If could be a library for PHP or JS, or maybe a simple NPM add on. In all cases, the name you pick should be unique.

    This gets hard when you want to name a tool something like “Foo for Bar” like “Color Coding for Quickbooks.” Wy is that hard? Well while your name is certainly descriptive, it’s not unique. Because someone else can make the same tool. “Joe’s Color Coding for Quickbooks.” Or worse… “Color Coding 4 Quickbooks.” And the problem here is that neither of you really have the right to the name, do you? You’re both leveraging ‘Quickbooks’ and their brand, so where do you have a leg to stand on when someone uses a similar name?

    A unique name, though, like “Color Me Quickly,” would be so much better. Think of displaying it like this: “Color Me Quickly – A tool to colorize Quickbooks” and then having a description that talks about the idea and how to use it. “We love Quickbooks, just like you, but we hated the color schemes. We were always mixing up Receipts and Refunds. That’s why we came up with the Color Me Quickly tool. One simple install and we could see, right away, what was what. With our accessibility friendly default color schemes, and fully customizable colors, you can make your Quickbooks look how you need.”

    The name is unique, the description is SEO friendly, and you will be easily able to stand out in a crowd.

    Function Names

    Oh but then we have function names.

    If you’re a library, please please please remember to wrap your code in “If this code is already included, do not include it again” checks. PHP has function_exists() and class_exists().

    Using Javascript?

    if (typeof obj === "function") { 
        // Function is safe to use
    }
    

    The point here is that if you’ve made a library, always make sure it’s not already running before you try to run. This is a huge issue in WordPress land. With over 45,000 plugins, the odds that two will include the same libraries are pretty high. The odds that two will have conflicting versions? Right, you got it.

    But you should watch out with those checks. I’ve seen a lot of plugins use a check that if the function doesn’t exist, run their plugin. That’s a great idea, except that it’s not. If you name your function wp_get_post() and check for it’s existence before loading, what happens if it does exist? Your code won’t be called. And what happens if your code doesn’t get called? Your function won’t run. Your plugin won’t work as expected.

    Function and class names have to consider their world. A WordPress plugin should never use a non-prefixed’ anything. As Nacin says:

    It’s a simple concept. Anything you create in the global namespace has the potential to conflict with a theme, another plugin (including one you wrote), and WordPress core itself. Thus, prefix everything with a unique-enough character set.

    Be Unique

    Consider the environment that you code for when you name things. Always check for trademarks and possible conflicts before you name something you plan to release to the world. Remember to be unique.

    Also remember it’s 2016. All the good two and three character prefixes are probably taken.

  • Too Many SVGs

    Too Many SVGs

    I was looking into moving a site from Font Icons to SVGs for a few reasons. The primary is that, with an SVG, images will look crisp on all monitors, including the non-retina displays. They literally look better on my crappy old MacBook, instead of just on my iPad.

    Once I had the one site done, I went to look at another. It was a smaller site, running a Hugo as a static site generator, and I thought it would be perfect.

    I was wrong.

    Using SVGs is Easy

    Replacing my font icon with an SVG was as easy as making my Facebook call this:

    <object type="image/svg+xml" data="/images/social/facebook.svg"><span class="screen-reader-text">Facebook</span></object>
    

    Done. It’s tiny (2kb) and there are six similarly sized images which makes for 18kb which is incredibly smaller than the 200kb or more that Font Awesome can be. Simply, I realized I was only using five of the icons (on every page) and how stupid was that? I don’t need the whole library!

    I will note that ‘styling’ SVGs can be an exercise in patience, since you cannot apply CSS styles when you embed as an object. Thankfully, I wanted to make the icon match my style so I edited the style directly (which is the topic of another post). If you use PHP, I recommend using file_get_contents() to get the contents of the svg, and then use normal CSS to style. I was using plain HTML. There are tradeoffs.

    Using too many SVGs sucks

    My initial tests, using the footer first, and my page loaded much faster. Elated, I jumped over to all uses of the fonts, and remembered I had a page that listed a series of items with star rankings (none through five). I changed the generator code behind that to be object icons and reloaded.

    The page was slow.

    It was like dialup modem slow. Absolutely painful.

    After some research, I ran into this post about why SVG was so slow, and found a graphic that explained it clearly.

    Render times per number of objects on a page

    What the graph demonstrates is simply that the more objects you have on a page, the slower it is. That part is obvious. The more anything on a page, the slower it is. So why are SVGs slower than PNGs? Why was I only seeing this on an HTML page with 50 images, and not on a WordPress generated PHP page with the same amount.

    The answer was because the SVGs have to be rendered on the HTML page. I was using <object> tags on the HTML and file_get_contents on the PHP. The way the PHP code works, it pulls the file into content and dumps it out, not processing. Since the files are so small, and since the there’s no object rendering involved, the rendered PHP was faster than a static HTML. In this case.

    Can It Be Faster?

    After I was done face-palming, I asked myself if it was possible to speed this up? Fixing this comes with understanding the cause. Once I determined that the issue was rendering the object and not the SVG itself, the solution unfurled before me.

    Instead of using object tags, I could include SVGs like this:

    <svg version="1.1" id="facebook" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" 
    x="0px" y="0px" width="50px" height="50px" viewBox="0 0 438.536 438.536" 
    style="enable-background:new 0 0 438.536 438.536;" xml:space="preserve">
    <g>
    <path class="social" d="M414.41,24.123C398.333,8.042,378.963,0,356.315,0H82.228C59.58,0,40.21,8.042,24.126,24.123 C8.045,40.207,0.003,59.576,0.003,82.225v274.084c0,22.647,8.042,42.018,24.123,58.102c16.084,16.084,35.454,24.126,58.102,24.126 
    h274.084c22.648,0,42.018-8.042,58.095-24.126c16.084-16.084,24.126-35.454,24.126-58.102V82.225 C438.532,59.576,430.49,40.204,414.41,24.123z 
    M373.155,225.548h-49.963V406.84h-74.802V225.548H210.99V163.02h37.401v-37.402 
    c0-26.838,6.283-47.107,18.843-60.813c12.559-13.706,33.304-20.555,62.242-20.555h49.963v62.526h-31.401 
    c-10.663,0-17.467,1.853-20.417,5.568c-2.949,3.711-4.428,10.23-4.428,19.558v31.119h56.534L373.155,225.548z"/>
    </g></svg>
    

    The downside is that this looks uglier. The upside? This is hella fast and it’s still lighter weight than including a font icon, and I don’t have to upload images.

    SVGs or Font Icons?

    This is a question for the ages. They can both be made accessibility friendly, they can both be optimized. Arguably, font icons are compatible with more browsers, but it’s also 2016 and if people are still on IE 8 (sorry banks), the Internet looks pretty shitty anyway. I can’t tell you which is better, and I find use for both in different situations. I love font icons a great deal, but just as I love WordPress, there’s a time and a place for them. And a time and a place for something else.

  • Null and Zero

    Null and Zero

    This is an amusing anecdote.

    When I was working on my cross-check of shows and characters, I got everything working right except one thing. I noticed my count of ‘shows with death’ made a weird pie chart. You see, the number of shows was off by one compared to the total number of shows. I went back and forth, trying to figure out why it was doing that, and in the end I decided that I’d output the list and manually count to see what I was missing.

    I counted, by hand, the shows that I got with the list of ‘all characters are dead’ and that number matched what the code output. Then I subtracted that from the number of ‘shows with any death’ to get the ‘some characters are dead’ count, and that too was okay. This meant that, for some reason, the list of shows where no one died was wrong. But it was subtraction! How could it be wrong!

    Well as it turns out, I forgot that null and zero aren’t the same to a computer, but they tend to be to a human’s brain.

    Now I know this! I know that zero is a number, it’s a value of the known quantity of zero. And I know that ‘null’ is a non value, meaning that it’s a data point that cannot yet be known.

    You can’t math on null. And I knew this. Earlier in my code I’d written $foo = 0 outside of my loop where I check and, as needed, increment it with $foo++ specifically because you can’t add to null.

    Nothing from nothing, carry the nothing…

    But. In my calculations, I checked the following:

    1. If a show has been flagged with ‘death,’ count all the characters.
    2. For each character, if they’re dead, add 1 to the death count.
    3. If the number of characters is the same as the death count, add this show to the list of ‘kill ’em all.’
    4. If the number of characters is greater than the number of dead, and the value of either isn’t 0, add the show to the list of ‘kill some.’

    Then, separately, I checked “If the show has not been flagged with death, add the show to the ‘kill none’ list, because that’s a 1/0 check. And when you don’t think too deeply about that, it sounds fine, right? If they aren’t marked with death they must kill none. And if they don’t kill them all, and they don’t kill some, then the number should be the same as the ‘kill none’ list.

    The problem was that I had one show, just one, where all the characters were alive but it had been flagged with death. This was not an error. The show did kill off a character, but I’d not added the dead character yet. Which meant it ran through the checks like this:

    1. Flagged with death, we count all the characters (8).
    2. If the character is dead, add one to death count (death count is 0).
    3. If the number of characters (8) is the same as the dead (0), add to ‘kill them all’ (false).
    4. If the number of characters (8) is more than the dead (0) (true), add the value of either isn’t 0 (false), add them to ‘kill some.’ (false).

    Which isn’t wrong at all. It just meant that the show didn’t get listed on ‘kill none’ because it was flagged with dead, and it didn’t get listed on ‘kill them all’ because 8 is more than 0, and it didn’t get listed on ‘kill some’ because while 8 is more than 0, dead was 0.

    Oh silly me. The value of death characters was ‘null.’ They simply didn’t exist in a place where they should have.

    The fix? I added the dead character to the site and everything was fixed. But code wise, could I prevent this? I certainly should, since I know better than many that you can’t predict what users are going to do. So it begs the question of why was I checking if character count and dead count were not 0 to begin with? It was, originally, because my ‘no deaths’ list was screwed up and I threw that check in to omit cases where a show was flagged as death but didn’t have death.

    The accuracy of these things depends entirely on your data. Garbage in, garbage out. The best fix would be to check ‘if a show has death and it has no dead characters, adjust the dead count down by one’ but also ‘if a show has no death, but it has dead characters, adjust the live show count down by one.’ I haven’t done that yet. I will soon.

  • Mailbag: Why Do Cannonical URLs Mess Me Up?

    Mailbag: Why Do Cannonical URLs Mess Me Up?

    This came from a DreamHoster who said it was okay to blog it if I didn’t mention them by name. They were embarrassed about the mistake.

    Why was my site having a redirect loop, and why did changing the domain to force www in panel fix it?

    The ‘panel’ being mentioned here is DreamHost’s Panel. We don’t have cPanel, we have PANEL, and it’s our special, 100%, tool. In there, you can edit your domain settings. One of the settings has to do with your domain settings. Simply it asks “Do you want the www in your URL?”

    DreamHost Panel: Do you want www or not?

    In general I check “no” because I’m a no-www kind of person. I don’t like it.

    The issue this person was faceing was that you’d go to http://www.wordpress.dev and everything was fine, but his site went all over the place weird when you went to

    In order to fix that person’s website, I changed “Leave it alone” to “Add WWW” (their preference, not mine).

    Why did that work? Let’s understand the issue first. What was happening was that your server generally doesn’t care if you visit http://www.wordpress.dev or http://wordpress.dev because it knows that they both mean /home/user/wordpress/public_html/ (or whatever). But! Some servers (like DreamHost) let you prioritize and redirect. If they don’t, you can use nginx/htaccess to force www or not. As far as the server cares, none of this matters. If you force no-www and someone goes to www, they get redirected and everyone’s happy.

    Except WordPress. WordPress is picky. WordPress has special settings:

    Your home and site URLs in WP

    Recognize that? If you have WordPress set to use www and you go to the non-www URL, it won’t redirect you. It will, however, force all internal links and generated paths to have the www. The same thing happens if you don’t force https for your site. WordPress will still serve http://wordpress.dev but all the links on that page would be to https://wordpress.dev and so will your stylesheets and javascript.

    This may make you think that WordPress doesn’t care. You’d be wrong. WordPress cares deeply, and it shows up when you go a URL like http://wordpress.dev/i-am-fake/ – assuming you don’t have a page named that. If you’ve forced www, WordPress will look for that page and do a 404 redirect. Suddenly you’ll have www!

    Except in some cases, what happens is WordPress accepts the URL you gave it and shows without the www. Then it remembers it should have the www and redirects to that. Only it knows you told it non-www and redirects to that. And you get an endless 301 redirect loop. And you cry.

    If you force www in DreamHost’s Panel and you force it in htaccess and you set it your settings, this still may not be enough! You may have to do a search and replace to change all the non-www urls to www!

    Amusingly, when WordPress 4.4.1 dropped, we found a rare race condition with http and https and WooCommerce, born from a simple mistake.

    Woo lets you force http on post-checkout pages

    Everyone I know who looked at that went “Oh, right, if my site has https in the home and site URLs, maybe I shouldn’t try to force http here!” But Woo lets you shoot yourself in the foot. Or at least they did. There’s a ticket open where I suggested perhaps they prevent that.

    And for what it’s worth, I totally get how these things happen. You set up your domain and your WordPress site and your http/https settings at different times. It’s understandable that in 2013 you didn’t have SSL, but you added it in 2014. And at that time, you only put SSL on your checkout pages (right?) and since you wanted your cache to work better, you said “no https for checkout’ed!” That’s perfectly sane and logical. But since LetsEncrypt and HTTPS Everywhere became big in 2015, you changed the whole site over and simply forgot about that one, teensy, toggle…

    At least, until someone got that horrible 301 redirect on checkout.

    Like I told the people I fixed, don’t kick yourself over this. You have a lot of moving parts and the secret is understanding how each bit works. If you know that you set Panel properly, and .htaccess properly, and site/home URLs properly, and it only happens on checkout, you can zero in on what’s left and debug that.

  • Why CDN Media Needs a Plugin

    Why CDN Media Needs a Plugin

    I wanted to write a blog post for work (something I try to do once a month) so I thought “I should write about using a CDN for images. I wonder if you can do this without a plugin…”

    One hour later, and 1200 words, the answer is no. You cannot.

    My initial goal was to move media files (and only the media) from http://example.com/wp-content/uploads/ to http://static.example.com/wordpress/ on DreamObjects. I’ve written a plugin that does that, but to my frustration, I found you cannot do this without a plugin for one incredibly simple reason.

    But before the big reveal, let’s break down, in simple terms, what I would actually need to do in order to move the uploads. My two assumptions are that I already have a WordPress powered site (check) and I already have DreamObjects (check)

    1. Setup a bucket on DreamObjects (or AWS whatever) to house my images, and give it a CDN alias.
    2. Copy all the images to the bucket.
    3. Change the Upload URL to http://static.example.com/wordpress/ (my CDN alias for the bucket).
    4. Edit all posts and GUIDs to the new URL.

    The thing is, I can actually do all of that!

    Setup a Bucket on DreamObjects

    Log in to your Panel, click on Cloud, go to DreamObjects, and create a new bucket in DreamObjects. I called my domain-static because that’s easy for me to remember. Static content lives here. Once you have your bucket, click on the “Change Settings” link and add an alias of “static” to the domain you’re hosting all this on (example.com in this example).

    You can name your alias anything you want. I just picked static because I knew I wanted my URLs for images to be http://static.example.com/wordpress/2016/01/happynew.jpg and this makes it simple. I like to leave my CDN available for more than just WordPress, and doing this will let me have more folders like wiki or gallery.

    Next, scroll down to “DreamSpeed CDN” and turn on CDN Support. You’ll notice that tells you a special URL for CDN:

    Connect to the accelerated DreamSpeed CDN version of this bucket at: examplecom-uploads.objects-us-east-1.dream.io

    Don’t worry! You can use your custom URL too. You don’t have to, but most of us want to, to feel special. In order to use your custom alias that we just made, scroll up a little and check the box for ‘CDN’ on your alias. Press save and you’re good to go!

    Copy all the Images

    Set the bucket public first!

    Just trust me, here. Okay? Good. Set the bucket public and then upload all the images. I used Transmit. Cyberduck also works.

    Change the Upload URL

    This part was scary.

    We need a moment of history first. Up until WordPress 3.5 this was actually pretty easy to do. You went to your media page and you changed things. As of 3.5, WordPress decided that this was more trouble than it was worth. Too many people were accidentally doing silly things, breaking their sites, and it was too dangerous. So they removed the part of the screen that let you change this.

    I have issues with this, since for what I want to do, it makes it a hassle. But given the flaw in my great plan, I recognize the change as one that protects people who know less than I do.

    Using a plugin to restore this missing setting would be the easiest on many levels. And there are a few plugins that do this but I like Upload Url and Path Enabler. It’s simple and to the point.

    Of course, I love wp-cli and we have it on all our servers at DreamHost, so this command is similarly awesome:

    wp option set upload_url_path http://static.example.com/wordpress

    The last option for this is the secret WordPress page called “All Settings” — This is hands down the most powerful and dangerous page in all of WordPress. It lists all your options and settings that you have in the database. And yes, you can edit many of them in your browser at http://example.com/wp-admin/options.php

    Go ahead. Take a look. It lists a lot of things, most of which you should never, ever, ever, touch. If you were going to use this, search for upload_url_path, change the value from empty to http://static.example.com/wordpress, and press save.

    Edit All Your Posts

    This is a sucky part. You have to edit all your posts now to move the existing images. This is because those changes you made are only for images going forward. Which is really cool and means you didn’t break anything so far. But WordPress hardcodes the paths to images in your posts (for many reasons) so you need to change all of them.

    If you know how to use the command line, this is actually really easy:

    wp search-replace http://example.com/wp-content/uploads/ http://static.example.com/wordpress/

    Run that command and WP-CLI will magically fix all your posts.

    If you don’t want to use the command line, I recommend Velvet Blues Update URLs.

    Done!

    And to be clear on things, this worked perfectly. My media library showed properly, all my images showed, and everything looked perfect. So I decided to run some basic tests and upload new images…. and that’s where my house of cards fell apart.

    You cannot save files to another server.

    Actually You Can… if you sudo

    Now I have to tell you something. I lied. You totally can do this. The problem is that it’s hard and requires mounting your bucket as a local filesystem so that it would be available via the file-path of the server. You see, you could save files to /folder/location/wordpress/ anywhere on the server. I save mine to /home/user/public_html/static/ on one set up, and I have a static domain (domain-static.com) that runs from that folder.

    What that means if I had a location I could access, I could tell WordPress to save there, making it ‘local’ enough to trick it. You can do this with tools like s3fs-fuse, however they’re incredibly complicated and weird for the layman. And that right there was my problem.

    If you’re trying to present something as ‘Without a plugin’ then you don’t want to make the tradeoff be ‘..but with sudo access to a VPS.’ That’s unreasonable.

    And it’s why, right now, if you want to use a CDN for your media in WordPress, use a plugin.